]>
Commit | Line | Data |
---|---|---|
23c9e63c DD |
1 | /* |
2 | * Copyright (c) 2000, Red Hat, Inc. | |
3 | * | |
4 | * This program is free software; you can redistribute it and/or modify | |
5 | * it under the terms of the GNU General Public License as published by | |
6 | * the Free Software Foundation; either version 2 of the License, or | |
7 | * (at your option) any later version. | |
8 | * | |
9 | * A copy of the GNU General Public License can be found at | |
10 | * http://www.gnu.org/ | |
11 | * | |
12 | * Written by DJ Delorie <dj@cygnus.com> | |
13 | * | |
14 | */ | |
15 | ||
16 | /* The purpose of this file is to act as a pretty interface to | |
17 | netio.cc. We add a progress dialog and some convenience functions | |
18 | (like collect to string or file */ | |
19 | ||
8507f105 DD |
20 | static char *cvsid = "\n%%% $Id$\n"; |
21 | ||
23c9e63c DD |
22 | #include "win32.h" |
23 | #include "commctrl.h" | |
24 | ||
25 | #include <stdio.h> | |
26 | #include <stdlib.h> | |
27 | #include <errno.h> | |
28 | ||
29 | #include "dialog.h" | |
30 | #include "geturl.h" | |
31 | #include "resource.h" | |
32 | #include "netio.h" | |
33 | #include "msg.h" | |
89b1a15b | 34 | #include "log.h" |
2f9645a1 CV |
35 | #include "state.h" |
36 | #include "diskfull.h" | |
85b43844 | 37 | #include "mount.h" |
23c9e63c DD |
38 | |
39 | static int is_showing = 0; | |
40 | static HWND gw_dialog = 0; | |
41 | static HWND gw_url = 0; | |
42 | static HWND gw_rate = 0; | |
43 | static HWND gw_progress = 0; | |
2f9645a1 CV |
44 | static HWND gw_pprogress = 0; |
45 | static HWND gw_iprogress = 0; | |
46 | static HWND gw_progress_text = 0; | |
47 | static HWND gw_pprogress_text = 0; | |
48 | static HWND gw_iprogress_text = 0; | |
23c9e63c DD |
49 | static HANDLE init_event; |
50 | static int max_bytes = 0; | |
51 | ||
2f9645a1 CV |
52 | int total_download_bytes = 0; |
53 | int total_download_bytes_sofar = 0; | |
54 | ||
23c9e63c DD |
55 | static BOOL |
56 | dialog_cmd (HWND h, int id, HWND hwndctl, UINT code) | |
57 | { | |
58 | switch (id) | |
59 | { | |
60 | case IDCANCEL: | |
89b1a15b | 61 | exit_setup (0); |
23c9e63c DD |
62 | } |
63 | } | |
64 | ||
65 | static BOOL CALLBACK | |
66 | dialog_proc (HWND h, UINT message, WPARAM wParam, LPARAM lParam) | |
67 | { | |
68 | int i, j; | |
69 | HWND listbox; | |
70 | switch (message) | |
71 | { | |
72 | case WM_INITDIALOG: | |
73 | gw_dialog = h; | |
74 | gw_url = GetDlgItem (h, IDC_DLS_URL); | |
75 | gw_rate = GetDlgItem (h, IDC_DLS_RATE); | |
76 | gw_progress = GetDlgItem (h, IDC_DLS_PROGRESS); | |
2f9645a1 CV |
77 | gw_pprogress = GetDlgItem (h, IDC_DLS_PPROGRESS); |
78 | gw_iprogress = GetDlgItem (h, IDC_DLS_IPROGRESS); | |
79 | gw_progress_text = GetDlgItem (h, IDC_DLS_PROGRESS_TEXT); | |
80 | gw_pprogress_text = GetDlgItem (h, IDC_DLS_PPROGRESS_TEXT); | |
81 | gw_iprogress_text = GetDlgItem (h, IDC_DLS_IPROGRESS_TEXT); | |
23c9e63c DD |
82 | SetEvent (init_event); |
83 | return FALSE; | |
84 | case WM_COMMAND: | |
1fd6d0a2 | 85 | return HANDLE_WM_COMMAND (h, wParam, lParam, dialog_cmd); |
23c9e63c DD |
86 | } |
87 | return FALSE; | |
88 | } | |
89 | ||
90 | static WINAPI DWORD | |
91 | dialog (void *) | |
92 | { | |
93 | int rv = 0; | |
94 | MSG m; | |
ed96c6da | 95 | HWND gw_dialog = CreateDialog (hinstance, MAKEINTRESOURCE (IDD_DLSTATUS), |
23c9e63c DD |
96 | 0, dialog_proc); |
97 | ShowWindow (gw_dialog, SW_SHOWNORMAL); | |
98 | UpdateWindow (gw_dialog); | |
99 | while (GetMessage (&m, 0, 0, 0) > 0) { | |
100 | TranslateMessage (&m); | |
101 | DispatchMessage (&m); | |
102 | } | |
103 | } | |
104 | ||
105 | static DWORD start_tics; | |
106 | ||
107 | static void | |
108 | init_dialog (char *url, int length) | |
109 | { | |
110 | if (gw_dialog == 0) | |
111 | { | |
112 | DWORD tid; | |
113 | HANDLE thread; | |
114 | init_event = CreateEvent (0, 0, 0, 0); | |
115 | thread = CreateThread (0, 0, dialog, 0, 0, &tid); | |
116 | WaitForSingleObject (init_event, 1000); | |
117 | CloseHandle (init_event); | |
118 | SendMessage (gw_progress, PBM_SETRANGE, 0, MAKELPARAM (0, 100)); | |
2f9645a1 CV |
119 | SendMessage (gw_pprogress, PBM_SETRANGE, 0, MAKELPARAM (0, 100)); |
120 | SendMessage (gw_iprogress, PBM_SETRANGE, 0, MAKELPARAM (0, 100)); | |
23c9e63c DD |
121 | is_showing = 0; |
122 | } | |
123 | char *sl=url, *cp; | |
124 | for (cp=url; *cp; cp++) | |
125 | if (*cp == '/' || *cp == '\\' || *cp == ':') | |
126 | sl = cp+1; | |
127 | max_bytes = length; | |
128 | SetWindowText (gw_url, sl); | |
129 | SetWindowText (gw_rate, "Connecting..."); | |
130 | SendMessage (gw_progress, PBM_SETPOS, (WPARAM) 0, 0); | |
131 | ShowWindow (gw_progress, (length > 0) ? SW_SHOW : SW_HIDE); | |
2f9645a1 CV |
132 | if (length > 0 ) |
133 | SetWindowText (gw_progress_text, "Package"); | |
134 | else | |
135 | SetWindowText (gw_progress_text, " "); | |
136 | ShowWindow (gw_pprogress, (total_download_bytes > 0) ? SW_SHOW : SW_HIDE); | |
137 | if (total_download_bytes > 0) | |
138 | { | |
139 | SetWindowText (gw_pprogress_text, "Total"); | |
140 | SetWindowText (gw_iprogress_text, "Disk"); | |
141 | } | |
42bf5b92 | 142 | else |
2f9645a1 CV |
143 | { |
144 | SetWindowText (gw_pprogress_text, " "); | |
145 | SetWindowText (gw_iprogress_text, " "); | |
146 | } | |
147 | ShowWindow (gw_iprogress, (total_download_bytes > 0) ? SW_SHOW : SW_HIDE); | |
23c9e63c DD |
148 | ShowWindow (gw_dialog, SW_SHOWNORMAL); |
149 | if (!is_showing) | |
150 | { | |
151 | SetForegroundWindow (gw_dialog); | |
152 | is_showing = 1; | |
153 | } | |
1fd6d0a2 | 154 | start_tics = GetTickCount (); |
23c9e63c DD |
155 | } |
156 | ||
157 | ||
158 | static void | |
159 | progress (int bytes) | |
160 | { | |
161 | static char buf[100]; | |
162 | int kbps; | |
163 | static int last_tics = 0; | |
1fd6d0a2 | 164 | DWORD tics = GetTickCount (); |
23c9e63c DD |
165 | if (tics == start_tics) // to prevent division by zero |
166 | return; | |
167 | if (tics < last_tics + 200) // to prevent flickering updates | |
168 | return; | |
169 | last_tics = tics; | |
170 | ||
171 | kbps = bytes / (tics - start_tics); | |
172 | ShowWindow (gw_progress, (max_bytes > 0) ? SW_SHOW : SW_HIDE); | |
2f9645a1 CV |
173 | ShowWindow (gw_pprogress, (total_download_bytes > 0) ? SW_SHOW : SW_HIDE); |
174 | ShowWindow (gw_iprogress, (total_download_bytes > 0) ? SW_SHOW : SW_HIDE); | |
bf1d5889 | 175 | if (max_bytes > 100) |
23c9e63c | 176 | { |
bf1d5889 | 177 | int perc = bytes / (max_bytes / 100); |
23c9e63c | 178 | SendMessage (gw_progress, PBM_SETPOS, (WPARAM) perc, 0); |
1fd6d0a2 DD |
179 | sprintf (buf, "%3d %% (%dk/%dk) %d kb/s\n", |
180 | perc, bytes/1000, max_bytes/1000, kbps); | |
2f9645a1 CV |
181 | if (total_download_bytes > 0) |
182 | { | |
183 | int totalperc = (total_download_bytes_sofar + bytes) / ( | |
184 | total_download_bytes / 100); | |
185 | SendMessage (gw_pprogress, PBM_SETPOS, (WPARAM) totalperc, 0); | |
186 | } | |
23c9e63c DD |
187 | } |
188 | else | |
1fd6d0a2 | 189 | sprintf (buf, "%d %d kb/s\n", bytes, kbps); |
23c9e63c DD |
190 | |
191 | SetWindowText (gw_rate, buf); | |
192 | } | |
193 | ||
194 | struct GUBuf { | |
195 | GUBuf *next; | |
196 | int count; | |
197 | char buf[2000]; | |
198 | }; | |
199 | ||
200 | char * | |
201 | get_url_to_string (char *_url) | |
202 | { | |
89b1a15b | 203 | log (LOG_BABBLE, "get_url_to_string %s", _url); |
23c9e63c DD |
204 | init_dialog (_url, 0); |
205 | NetIO *n = NetIO::open (_url); | |
206 | if (!n || !n->ok ()) | |
207 | { | |
208 | delete n; | |
89b1a15b | 209 | log (LOG_BABBLE, "get_url_to_string failed!"); |
23c9e63c DD |
210 | return 0; |
211 | } | |
212 | ||
213 | if (n->file_size) | |
214 | max_bytes = n->file_size; | |
215 | ||
216 | GUBuf *bufs = 0; | |
217 | GUBuf **nextp = &bufs; | |
218 | int total_bytes = 1; /* for the NUL */ | |
219 | progress (0); | |
220 | while (1) | |
221 | { | |
222 | GUBuf *b = new GUBuf; | |
223 | *nextp = b; | |
224 | b->next = 0; | |
225 | nextp = &(b->next); | |
226 | ||
227 | b->count = n->read (b->buf, sizeof (b->buf)); | |
228 | if (b->count <= 0) | |
229 | break; | |
230 | total_bytes += b->count; | |
231 | progress (total_bytes); | |
232 | } | |
233 | ||
234 | char *rv = (char *) malloc (total_bytes); | |
235 | char *rvp = rv; | |
236 | while (bufs && bufs->count > 0) | |
237 | { | |
238 | GUBuf *tmp = bufs->next; | |
239 | memcpy (rvp, bufs->buf, bufs->count); | |
240 | rvp += bufs->count; | |
241 | delete bufs; | |
242 | bufs = tmp; | |
243 | } | |
244 | *rvp = 0; | |
245 | return rv; | |
246 | } | |
247 | ||
248 | int | |
249 | get_url_to_file (char *_url, char *_filename, int expected_length) | |
250 | { | |
89b1a15b | 251 | log (LOG_BABBLE, "get_url_to_file %s %s", _url, _filename); |
2f9645a1 CV |
252 | if (total_download_bytes > 0) |
253 | { | |
85b43844 | 254 | int df = diskfull (get_root_dir ()); |
2f9645a1 CV |
255 | SendMessage (gw_iprogress, PBM_SETPOS, (WPARAM) df, 0); |
256 | } | |
23c9e63c DD |
257 | init_dialog (_url, expected_length); |
258 | ||
259 | remove (_filename); /* but ignore errors */ | |
260 | ||
261 | NetIO *n = NetIO::open (_url); | |
262 | if (!n || !n->ok ()) | |
263 | { | |
264 | delete n; | |
89b1a15b | 265 | log (LOG_BABBLE, "get_url_to_file failed!"); |
23c9e63c DD |
266 | return 1; |
267 | } | |
268 | ||
1fd6d0a2 | 269 | FILE *f = fopen (_filename, "wb"); |
23c9e63c DD |
270 | if (!f) |
271 | { | |
272 | char *err = strerror (errno); | |
273 | if (!err) | |
274 | err = "(unknown error)"; | |
275 | fatal (IDS_ERR_OPEN_WRITE, _filename, err); | |
276 | } | |
277 | ||
278 | if (n->file_size) | |
279 | max_bytes = n->file_size; | |
280 | ||
281 | int total_bytes = 0; | |
282 | progress (0); | |
283 | while (1) | |
284 | { | |
4a83b7b0 | 285 | char buf[8192]; |
23c9e63c DD |
286 | int count; |
287 | count = n->read (buf, sizeof (buf)); | |
288 | if (count <= 0) | |
289 | break; | |
290 | fwrite (buf, 1, count, f); | |
291 | total_bytes += count; | |
292 | progress (total_bytes); | |
293 | } | |
294 | ||
2f9645a1 CV |
295 | total_download_bytes_sofar += total_bytes; |
296 | ||
23c9e63c DD |
297 | fclose (f); |
298 | ||
2f9645a1 CV |
299 | if (total_download_bytes > 0) |
300 | { | |
85b43844 | 301 | int df = diskfull (get_root_dir ()); |
2f9645a1 CV |
302 | SendMessage (gw_iprogress, PBM_SETPOS, (WPARAM) df, 0); |
303 | } | |
304 | ||
23c9e63c DD |
305 | return 0; |
306 | } | |
307 | ||
308 | void | |
309 | dismiss_url_status_dialog () | |
310 | { | |
311 | ShowWindow (gw_dialog, SW_HIDE); | |
312 | is_showing = 0; | |
313 | } |