448
+ − 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 let the user choose which packages
+ − 17 to install, and which versions of the package when more than one
+ − 18 version is provided. The "trust" level serves as an indication as
+ − 19 to which version should be the default choice. At the moment, all
+ − 20 we do is compare with previously installed packages to skip any
+ − 21 that are already installed (by setting the action to ACTION_SAME).
+ − 22 While the "trust" stuff is supported, it's not really implemented
+ − 23 yet. We always prefer the "current" option. In the future, this
+ − 24 file might have a user dialog added to let the user choose to not
+ − 25 install packages, or to install packages that aren't installed by
+ − 26 default. */
+ − 27
+ − 28 #include "win32.h"
+ − 29 #include <stdio.h>
+ − 30 #include <stdlib.h>
+ − 31 #include <ctype.h>
+ − 32
+ − 33 #include "dialog.h"
+ − 34 #include "resource.h"
+ − 35 #include "state.h"
+ − 36 #include "ini.h"
+ − 37 #include "concat.h"
+ − 38 #include "msg.h"
+ − 39 #include "log.h"
+ − 40 #include "find.h"
+ − 41 #include "reginfo.h"
+ − 42
+ − 43 #define HMARGIN 10
+ − 44 #define ROW_MARGIN 5
+ − 45 #define ICON_MARGIN 4
+ − 46
+ − 47 #define CHECK_SIZE 11
+ − 48
+ − 49 #define TRUST_KEEP 101
+ − 50 #define TRUST_UNINSTALL 102
+ − 51 #define TRUST_NONE 103
+ − 52
+ − 53 static int initialized = 0;
+ − 54
+ − 55 static int full_list = 0;
+ − 56
+ − 57 static int scroll_ulc_x, scroll_ulc_y;
+ − 58
+ − 59 static HWND lv, nextbutton;
+ − 60 static TEXTMETRIC tm;
+ − 61 static int header_height;
+ − 62 static HANDLE sysfont;
+ − 63 static int row_height;
+ − 64 static HANDLE bm_spin, bm_rtarrow, bm_checkyes, bm_checkno, bm_checkna;
+ − 65 static HDC bitmap_dc;
+ − 66
+ − 67 static struct {
+ − 68 char *text;
+ − 69 int slen;
+ − 70 int width;
+ − 71 int x;
+ − 72 } headers[] = {
+ − 73 { "Current", 7, 0, 0 },
+ − 74 #define CURRENT_COL 0
+ − 75 { "New", 3, 0, 0 },
+ − 76 #define NEW_COL 1
+ − 77 { "Src?", 4, 0, 0 },
+ − 78 #define SRC_COL 2
+ − 79 { "Package", 7, 0, 0 },
+ − 80 #define PACKAGE_COL 3
+ − 81 { 0, 0, 0, 0 }
+ − 82 };
+ − 83 #define NUM_COLUMNS (sizeof(headers)/(sizeof(headers[0]))-1)
+ − 84
+ − 85 int *package_indexes, nindexes;
+ − 86
+ − 87 struct ExtraPackageInfo {
+ − 88 char *installed_file; /* filename of previous "install" file */
+ − 89 char *installed_ver; /* version part */
+ − 90 int installed_size; /* ditto, size. */
+ − 91
+ − 92 int in_partial_list;
+ − 93 int pick;
+ − 94 int npick;
+ − 95 int which_is_installed; /* == TRUST* or -1 */
+ − 96
+ − 97 struct {
+ − 98 int src_avail;
+ − 99 int trust; /* may be keep or uninstall */
+ − 100 char *caption; /* ==0 at EOL */
+ − 101 } chooser[NTRUST+3]; /* one extra for NULL above */
+ − 102 };
+ − 103
+ − 104 static ExtraPackageInfo *extra;
+ − 105
+ − 106 static void
+ − 107 paint (HWND hwnd)
+ − 108 {
+ − 109 HDC hdc;
+ − 110 PAINTSTRUCT ps;
+ − 111 int x, y, i, ii;
+ − 112
+ − 113 hdc = BeginPaint (hwnd, &ps);
+ − 114
+ − 115 SelectObject (hdc, sysfont);
+ − 116
+ − 117 RECT cr;
+ − 118 GetClientRect (hwnd, &cr);
+ − 119
+ − 120 POINT p;
+ − 121
+ − 122 x = cr.left - scroll_ulc_x;
+ − 123 y = cr.top - scroll_ulc_y + header_height;
+ − 124
+ − 125
+ − 126 for (i=0; headers[i].text; i++)
+ − 127 {
+ − 128 TextOut (hdc, x+headers[i].x, 3, headers[i].text, headers[i].slen);
+ − 129 MoveToEx (hdc, x+headers[i].x, header_height-3, &p);
+ − 130 LineTo (hdc, x+headers[i].x+headers[i].width, header_height-3);
+ − 131 }
+ − 132
+ − 133 IntersectClipRect (hdc, cr.left, cr.top+header_height, cr.right, cr.bottom);
+ − 134
+ − 135 for (ii=0; ii<nindexes; ii++)
+ − 136 {
+ − 137 i = package_indexes[ii];
+ − 138 int r = y + ii * row_height;
+ − 139 int by = r + tm.tmHeight - 11;
+ − 140 if (extra[i].installed_ver && extra[i].installed_ver[0])
+ − 141 {
+ − 142 TextOut (hdc, x+headers[CURRENT_COL].x, r,
+ − 143 extra[i].installed_ver, strlen (extra[i].installed_ver));
+ − 144 SelectObject (bitmap_dc, bm_rtarrow);
+ − 145 BitBlt (hdc, x+headers[CURRENT_COL].x+headers[0].width+ICON_MARGIN/2+HMARGIN/2, by,
+ − 146 11, 11, bitmap_dc, 0, 0, SRCCOPY);
+ − 147 }
+ − 148
+ − 149 char *s = extra[i].chooser[extra[i].pick].caption;
+ − 150 if (s)
+ − 151 {
+ − 152 TextOut (hdc, x+headers[NEW_COL].x + 11 + ICON_MARGIN, r,
+ − 153 s, strlen (s));
+ − 154 if (extra[i].npick > 1)
+ − 155 {
+ − 156 SelectObject (bitmap_dc, bm_spin);
+ − 157 BitBlt (hdc, x+headers[NEW_COL].x, by, 11, 11,
+ − 158 bitmap_dc, 0, 0, SRCCOPY);
+ − 159 }
+ − 160 }
+ − 161
+ − 162 HANDLE check_bm = bm_checkna;
+ − 163 if (extra[i].chooser[extra[i].pick].src_avail)
+ − 164 {
+ − 165 if (package[i].srcaction == SRCACTION_NO)
+ − 166 check_bm = bm_checkno;
+ − 167 else if (package[i].srcaction == SRCACTION_YES)
+ − 168 check_bm = bm_checkyes;
+ − 169 }
+ − 170 SelectObject (bitmap_dc, check_bm);
+ − 171 BitBlt (hdc, x+headers[SRC_COL].x, by, 11, 11,
+ − 172 bitmap_dc, 0, 0, SRCCOPY);
+ − 173
+ − 174 if (package[i].name)
+ − 175 TextOut (hdc, x+headers[PACKAGE_COL].x, r, package[i].name, strlen(package[i].name));
+ − 176 }
+ − 177
+ − 178 if (nindexes == 0)
+ − 179 {
+ − 180 static char *m = "Nothing to Install/Update";
+ − 181 TextOut (hdc, HMARGIN, header_height, m, strlen (m));
+ − 182 }
+ − 183
+ − 184 EndPaint (hwnd, &ps);
+ − 185 }
+ − 186
+ − 187 static void
+ − 188 scroll_common (HWND hwnd, int which, int *var, int code)
+ − 189 {
+ − 190 SCROLLINFO si;
+ − 191 si.cbSize = sizeof (si);
+ − 192 si.fMask = SIF_ALL;
+ − 193 GetScrollInfo (hwnd, which, &si);
+ − 194
+ − 195 switch (code)
+ − 196 {
+ − 197 case SB_THUMBTRACK:
+ − 198 si.nPos = si.nTrackPos;
+ − 199 break;
+ − 200 case SB_THUMBPOSITION:
+ − 201 break;
+ − 202 case SB_BOTTOM:
+ − 203 si.nPos = si.nMax;
+ − 204 break;
+ − 205 case SB_TOP:
+ − 206 si.nPos = 0;
+ − 207 break;
+ − 208 case SB_LINEDOWN:
+ − 209 si.nPos += row_height;
+ − 210 break;
+ − 211 case SB_LINEUP:
+ − 212 si.nPos -= row_height;
+ − 213 break;
+ − 214 case SB_PAGEDOWN:
+ − 215 si.nPos += si.nPage * 9/10;
+ − 216 break;
+ − 217 case SB_PAGEUP:
+ − 218 si.nPos -= si.nPage * 9/10;
+ − 219 break;
+ − 220 }
+ − 221
+ − 222 if ((int)si.nPos < 0)
+ − 223 si.nPos = 0;
+ − 224 if ((int)(si.nPos + si.nPage) > si.nMax)
+ − 225 si.nPos = si.nMax - si.nPage;
+ − 226
+ − 227 si.fMask = SIF_POS;
+ − 228 SetScrollInfo (hwnd, which, &si, TRUE);
+ − 229
+ − 230 int ox = scroll_ulc_x;
+ − 231 int oy = scroll_ulc_y;
+ − 232 *var = si.nPos;
+ − 233
+ − 234 RECT cr, sr;
+ − 235 GetClientRect (hwnd, &cr);
+ − 236 sr = cr;
+ − 237 sr.top += header_height;
+ − 238 ScrollWindow (hwnd, ox - scroll_ulc_x, oy - scroll_ulc_y, &sr, &sr);
+ − 239 sr.bottom = sr.top;
+ − 240 sr.top = cr.top;
+ − 241 ScrollWindow (hwnd, ox - scroll_ulc_x, 0, &sr, &sr);
+ − 242 }
+ − 243
+ − 244 static LRESULT CALLBACK
+ − 245 list_vscroll (HWND hwnd, HWND hctl, UINT code, int pos)
+ − 246 {
+ − 247 scroll_common (hwnd, SB_VERT, &scroll_ulc_y, code);
+ − 248 return FALSE;
+ − 249 }
+ − 250
+ − 251 static LRESULT CALLBACK
+ − 252 list_hscroll (HWND hwnd, HWND hctl, UINT code, int pos)
+ − 253 {
+ − 254 scroll_common (hwnd, SB_HORZ, &scroll_ulc_x, code);
+ − 255 return FALSE;
+ − 256 }
+ − 257
+ − 258 static LRESULT CALLBACK
+ − 259 list_click (HWND hwnd, BOOL dblclk, int x, int y, UINT hitCode)
+ − 260 {
+ − 261 int r;
+ − 262
+ − 263 if (nindexes == 0)
+ − 264 return 0;
+ − 265
+ − 266 if (y < header_height)
+ − 267 return 0;
+ − 268 x += scroll_ulc_x;
+ − 269 y += scroll_ulc_y - header_height;
+ − 270
+ − 271 r = (y + ROW_MARGIN/2) / row_height;
+ − 272
+ − 273 if (r < 0 || r >= npackages)
+ − 274 return 0;
+ − 275
+ − 276 int p = package_indexes[r];
+ − 277
+ − 278 if (x >= headers[NEW_COL].x - HMARGIN/2 && x <= headers[NEW_COL+1].x - HMARGIN/2)
+ − 279 {
+ − 280 extra[p].pick ++;
+ − 281 if (extra[p].chooser[extra[p].pick].caption == 0)
+ − 282 extra[p].pick = 0;
+ − 283 }
+ − 284
+ − 285 if (x >= headers[SRC_COL].x - HMARGIN/2 && x <= headers[SRC_COL+1].x - HMARGIN/2)
+ − 286 {
+ − 287 if (extra[p].chooser[extra[p].pick].src_avail)
+ − 288 package[p].srcaction ^= (SRCACTION_NO^SRCACTION_YES);
+ − 289 }
+ − 290
+ − 291 RECT rect;
+ − 292 rect.left = headers[NEW_COL].x - scroll_ulc_x;
+ − 293 rect.right = headers[SRC_COL+1].x - scroll_ulc_x;
+ − 294 rect.top = header_height + r * row_height - scroll_ulc_y;
+ − 295 rect.bottom = rect.top + row_height;
+ − 296 InvalidateRect (hwnd, &rect, TRUE);
+ − 297 return FALSE;
+ − 298 }
+ − 299
+ − 300 static LRESULT CALLBACK
+ − 301 listview_proc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
+ − 302 {
+ − 303 switch (message) {
+ − 304 case WM_HSCROLL:
+ − 305 return HANDLE_WM_HSCROLL (hwnd, wParam, lParam, list_hscroll);
+ − 306 case WM_VSCROLL:
+ − 307 return HANDLE_WM_VSCROLL (hwnd, wParam, lParam, list_vscroll);
+ − 308 case WM_LBUTTONDOWN:
+ − 309 return HANDLE_WM_LBUTTONDOWN (hwnd, wParam, lParam, list_click);
+ − 310 case WM_PAINT:
+ − 311 paint (hwnd);
+ − 312 return 0;
+ − 313 default:
+ − 314 return DefWindowProc (hwnd, message, wParam, lParam);
+ − 315 }
+ − 316 }
+ − 317
+ − 318 static void
+ − 319 register_windows (HINSTANCE hinst)
+ − 320 {
+ − 321 WNDCLASSEX wcex;
+ − 322 static int done = 0;
+ − 323
+ − 324 if (done)
+ − 325 return;
+ − 326 done = 1;
+ − 327
+ − 328 memset (&wcex, 0, sizeof (wcex));
+ − 329 wcex.cbSize = sizeof (WNDCLASSEX);
+ − 330 wcex.style = CS_HREDRAW | CS_VREDRAW;
+ − 331 wcex.lpfnWndProc = listview_proc;
+ − 332 wcex.hInstance = hinst;
+ − 333 wcex.hIcon = LoadIcon (0, IDI_APPLICATION);
+ − 334 wcex.hCursor = LoadCursor (0, IDC_ARROW);
+ − 335 wcex.hbrBackground = (HBRUSH) (COLOR_WINDOW+1);
+ − 336 wcex.lpszClassName = "listview";
+ − 337
+ − 338 RegisterClassEx (&wcex);
+ − 339 }
+ − 340
+ − 341 static void
+ − 342 note_width (HDC dc, char *string, int addend, int column)
+ − 343 {
+ − 344 if (!string)
+ − 345 return;
+ − 346 SIZE s;
+ − 347 GetTextExtentPoint32 (dc, string, strlen (string), &s);
+ − 348 if (headers[column].width < s.cx + addend)
+ − 349 headers[column].width = s.cx + addend;
+ − 350 }
+ − 351
+ − 352 static int
+ − 353 best_trust (int p, int trust)
+ − 354 {
+ − 355 int t;
+ − 356 for (t=trust; t>=0; t--)
+ − 357 if (package[p].info[t].install)
+ − 358 return t;
+ − 359 for (t=trust+1; t<=NTRUST; t++)
+ − 360 if (package[p].info[t].install)
+ − 361 return t;
+ − 362 if (extra[p].installed_file)
+ − 363 return TRUST_KEEP;
+ − 364 return TRUST_NONE;
+ − 365 }
+ − 366
+ − 367 static void
+ − 368 default_trust (HWND h, int trust)
+ − 369 {
+ − 370 int i, t, c;
+ − 371
+ − 372 for (i=0; i<npackages; i++)
+ − 373 {
+ − 374 t = best_trust (i, trust);
+ − 375 extra[i].pick = 1;
+ − 376 for (c=0; c<extra[i].npick; c++)
+ − 377 if (t == extra[i].chooser[c].trust)
+ − 378 extra[i].pick = c;
+ − 379 if (install_type == IDC_INSTALL_NATIVE
+ − 380 && package[i].type == TY_CYGWIN
+ − 381 ||
+ − 382 install_type == IDC_INSTALL_CYGWIN
+ − 383 && package[i].type == TY_NATIVE)
+ − 384 extra[i].pick = extra[i].npick -1;
+ − 385 }
+ − 386 RECT r;
+ − 387 GetClientRect (h, &r);
+ − 388 InvalidateRect (h, &r, TRUE);
+ − 389 if (nextbutton)
+ − 390 SetFocus (nextbutton);
+ − 391 }
+ − 392
+ − 393 static void
+ − 394 set_full_list (HWND h, int isfull)
+ − 395 {
+ − 396 int i, j;
+ − 397 full_list = isfull;
+ − 398 if (package_indexes == 0)
+ − 399 package_indexes = (int *) malloc (npackages * sizeof (int));
+ − 400 for (i=j=0; i<npackages; i++)
+ − 401 {
+ − 402 if (isfull || extra[i].in_partial_list)
+ − 403 package_indexes[j++] = i;
+ − 404 }
+ − 405 nindexes = j;
+ − 406
+ − 407 RECT r;
+ − 408 GetClientRect (h, &r);
+ − 409 SCROLLINFO si;
+ − 410 memset (&si, 0, sizeof (si));
+ − 411 si.cbSize = sizeof (si);
+ − 412 si.fMask = SIF_ALL;
+ − 413 si.nMin = 0;
+ − 414 si.nMax = headers[2].x + headers[2].width + HMARGIN;
+ − 415 si.nPage = r.right;
+ − 416 SetScrollInfo (h, SB_HORZ, &si, TRUE);
+ − 417
+ − 418 si.nMax = nindexes * row_height;
+ − 419 si.nPage = r.bottom - header_height;
+ − 420 SetScrollInfo (h, SB_VERT, &si, TRUE);
+ − 421
+ − 422 scroll_ulc_x = scroll_ulc_y = 0;
+ − 423
+ − 424 InvalidateRect (h, &r, TRUE);
+ − 425
+ − 426 if (nextbutton)
+ − 427 SetFocus (nextbutton);
+ − 428 }
+ − 429
+ − 430 static void
+ − 431 build_labels ()
+ − 432 {
+ − 433 int i;
+ − 434 for (i=0; i<npackages; i++)
+ − 435 {
+ − 436 int c = 0, t;
+ − 437
+ − 438 #define C extra[i].chooser[c]
+ − 439 if (extra[i].installed_ver)
+ − 440 {
+ − 441 C.caption = "Uninstall";
+ − 442 C.trust = TRUST_UNINSTALL;
+ − 443 c++;
+ − 444 C.caption = "Keep";
+ − 445 C.trust = TRUST_KEEP;
+ − 446 c++;
+ − 447 }
+ − 448
+ − 449 for (t=TRUST_PREV; t<NTRUST; t++)
+ − 450 if (package[i].info[t].install)
+ − 451 if (t != extra[i].which_is_installed)
+ − 452 {
+ − 453 C.caption = package[i].info[t].version;
+ − 454 if (C.caption == 0 || C.caption[0] == 0)
+ − 455 C.caption = "0.0";
+ − 456 C.trust = t;
+ − 457 if (package[i].info[t].source)
+ − 458 C.src_avail = 1;
+ − 459 c++;
+ − 460 /* we intentionally skip TRUST_PREV */
+ − 461 if (t != TRUST_PREV || !extra[i].installed_ver)
+ − 462 extra[i].in_partial_list = 1;
+ − 463
+ − 464 }
+ − 465
+ − 466 if (c == 0)
+ − 467 {
+ − 468 C.caption = "N/A";
+ − 469 C.trust = TRUST_NONE;
+ − 470 c++;
+ − 471 }
+ − 472
+ − 473 if (! extra[i].installed_file)
+ − 474 {
+ − 475 C.caption = "Skip";
+ − 476 C.trust = TRUST_NONE;
+ − 477 c++;
+ − 478 }
+ − 479
+ − 480 C.caption = 0;
+ − 481 extra[i].npick = c;
+ − 482 #undef C
+ − 483 }
+ − 484 }
+ − 485
+ − 486 static void
+ − 487 create_listview (HWND dlg, RECT *r)
+ − 488 {
+ − 489 int i, t;
+ − 490 lv = CreateWindowEx (WS_EX_CLIENTEDGE,
+ − 491 "listview",
+ − 492 "listviewwindow",
+ − 493 WS_CHILD | WS_HSCROLL | WS_VSCROLL | WS_VISIBLE,
+ − 494 r->left, r->top,
+ − 495 r->right-r->left+1, r->bottom-r->top+1,
+ − 496 dlg,
+ − 497 NULL, // ??? MAKEINTRESOURCE(IDC_CHOOSE_LIST),
+ − 498 hinstance,
+ − 499 0);
+ − 500 ShowWindow (lv, SW_SHOW);
+ − 501
+ − 502 for (i=0; headers[i].text; i++)
+ − 503 headers[i].width = 0;
+ − 504
+ − 505 HDC dc = GetDC (lv);
+ − 506 sysfont = GetStockObject (DEFAULT_GUI_FONT);
+ − 507 SelectObject (dc, sysfont);
+ − 508 GetTextMetrics (dc, &tm);
+ − 509 header_height = tm.tmHeight + 5 + 3;
+ − 510
+ − 511 bitmap_dc = CreateCompatibleDC (dc);
+ − 512
+ − 513 row_height = (tm.tmHeight + tm.tmExternalLeading + ROW_MARGIN);
+ − 514 int irh = tm.tmExternalLeading + tm.tmDescent + 11 + ROW_MARGIN;
+ − 515 if (row_height < irh)
+ − 516 row_height = irh;
+ − 517
+ − 518 for (i=0; headers[i].text; i++)
+ − 519 note_width (dc, headers[i].text, 0, i);
+ − 520 for (i=0; i<npackages; i++)
+ − 521 {
+ − 522 note_width (dc, extra[i].installed_ver, 0, CURRENT_COL);
+ − 523 note_width (dc, extra[i].installed_ver, 11+ICON_MARGIN, NEW_COL);
+ − 524 for (t=0; t<NTRUST; t++)
+ − 525 note_width (dc, package[i].info[t].version, 11+ICON_MARGIN, NEW_COL);
+ − 526 note_width (dc, package[i].name, 0, PACKAGE_COL);
+ − 527 note_width (dc, package[i].sdesc, 0, PACKAGE_COL);
+ − 528 }
+ − 529 note_width (dc, "keep", 11+ICON_MARGIN, NEW_COL);
+ − 530 note_width (dc, "uninstall", 11+ICON_MARGIN, NEW_COL);
+ − 531
+ − 532 headers[CURRENT_COL].x = HMARGIN/2;
+ − 533 headers[NEW_COL].x = (headers[CURRENT_COL].x + headers[CURRENT_COL].width
+ − 534 + HMARGIN + 11 + ICON_MARGIN);
+ − 535 headers[SRC_COL].x = headers[NEW_COL].x + headers[NEW_COL].width + HMARGIN;
+ − 536 headers[PACKAGE_COL].x = headers[SRC_COL].x + headers[SRC_COL].width + HMARGIN;
+ − 537
+ − 538 set_full_list (lv, full_list);
+ − 539 default_trust (lv, TRUST_CURR);
+ − 540
+ − 541 ReleaseDC (lv, dc);
+ − 542 }
+ − 543
+ − 544 static BOOL
+ − 545 dialog_cmd (HWND h, int id, HWND hwndctl, UINT code)
+ − 546 {
+ − 547 switch (id)
+ − 548 {
+ − 549
+ − 550 case IDC_CHOOSE_PREV:
+ − 551 default_trust (lv, TRUST_PREV);
+ − 552 break;
+ − 553 case IDC_CHOOSE_CURR:
+ − 554 default_trust (lv, TRUST_CURR);
+ − 555 break;
+ − 556 case IDC_CHOOSE_EXP:
+ − 557 default_trust (lv, TRUST_TEST);
+ − 558 break;
+ − 559 case IDC_CHOOSE_FULLPART:
+ − 560 set_full_list (lv, !full_list);
+ − 561 break;
+ − 562
+ − 563 case IDOK:
+ − 564 if (source == IDC_SOURCE_CWD)
+ − 565 NEXT (IDD_S_INSTALL);
+ − 566 else
+ − 567 NEXT (IDD_S_DOWNLOAD);
+ − 568 break;
+ − 569
+ − 570 case IDC_BACK:
+ − 571 initialized = 0;
+ − 572 if (source == IDC_SOURCE_CWD)
+ − 573 NEXT (IDD_ROOT);
+ − 574 else
+ − 575 NEXT (IDD_SITE);
+ − 576 break;
+ − 577
+ − 578 case IDCANCEL:
+ − 579 NEXT (0);
+ − 580 break;
+ − 581 }
+ − 582 return FALSE;
+ − 583 }
+ − 584
+ − 585 static void
+ − 586 GetParentRect (HWND parent, HWND child, RECT *r)
+ − 587 {
+ − 588 POINT p;
+ − 589 GetWindowRect (child, r);
+ − 590 p.x = r->left;
+ − 591 p.y = r->top;
+ − 592 ScreenToClient (parent, &p);
+ − 593 r->left = p.x;
+ − 594 r->top = p.y;
+ − 595 p.x = r->right;
+ − 596 p.y = r->bottom;
+ − 597 ScreenToClient (parent, &p);
+ − 598 r->right = p.x;
+ − 599 r->bottom = p.y;
+ − 600 }
+ − 601
+ − 602 static BOOL CALLBACK
+ − 603 dialog_proc (HWND h, UINT message, WPARAM wParam, LPARAM lParam)
+ − 604 {
+ − 605 HWND frame;
+ − 606 RECT r;
+ − 607 switch (message)
+ − 608 {
+ − 609 case WM_INITDIALOG:
+ − 610 nextbutton = GetDlgItem (h, IDOK);
+ − 611 frame = GetDlgItem (h, IDC_LISTVIEW_POS);
+ − 612 GetParentRect (h, frame, &r);
+ − 613 r.top += 2;
+ − 614 r.bottom -= 2;
+ − 615 create_listview (h, &r);
+ − 616 #if 0
+ − 617 load_dialog (h);
+ − 618 #endif
+ − 619 return FALSE;
+ − 620 case WM_COMMAND:
+ − 621 return HANDLE_WM_COMMAND (h, wParam, lParam, dialog_cmd);
+ − 622 }
+ − 623 return FALSE;
+ − 624 }
+ − 625
657
+ − 626 char *
448
+ − 627 base (char *s)
+ − 628 {
+ − 629 if (!s)
+ − 630 return 0;
+ − 631 char *rv = s;
+ − 632 while (*s)
+ − 633 {
+ − 634 if ((*s == '/' || *s == ':' || *s == '\\') && s[1])
+ − 635 rv = s+1;
+ − 636 s++;
+ − 637 }
+ − 638 return rv;
+ − 639 }
+ − 640
+ − 641 static void
+ − 642 scan2 (char *path, unsigned int size)
+ − 643 {
+ − 644 int i, t;
+ − 645 for (i=0; i<npackages; i++)
+ − 646 for (t=0; t<NTRUST; t++)
+ − 647 if (package[i].info[t].install
+ − 648 && strcmp (base (package[i].info[t].install), base (path)) == 0
+ − 649 && package[i].info[t].install_size == (int)size)
+ − 650 {
+ − 651 extra[i].installed_file = package[i].info[t].install;
+ − 652 extra[i].installed_size = size;
+ − 653 extra[i].which_is_installed = t;
+ − 654 extra[i].installed_ver = package[i].info[t].version;
+ − 655 if (!extra[i].installed_ver)
+ − 656 extra[i].installed_ver = "0";
+ − 657 }
+ − 658 }
+ − 659
+ − 660 static void
+ − 661 scan_downloaded_files ()
+ − 662 {
+ − 663 find (".", scan2);
+ − 664 }
+ − 665
+ − 666 static void
+ − 667 read_installed_db ()
+ − 668 {
+ − 669 int i;
+ − 670 if (!root_dir)
+ − 671 return;
+ − 672
+ − 673 char line[1000], pkg[1000], inst[1000], src[1000];
+ − 674 int instsz, srcsz;
+ − 675
+ − 676 FILE *db = fopen (concat (root_dir, XEMACS_SETUP_DIR, "installed.db", 0), "rt");
+ − 677 if (!db)
+ − 678 return;
+ − 679
+ − 680 while (fgets (line, 1000, db))
+ − 681 {
+ − 682 src[0] = 0;
+ − 683 srcsz = 0;
+ − 684 sscanf (line, "%s %s %d %s %d", pkg, inst, &instsz, src, &srcsz);
+ − 685
+ − 686 for (i=0; i<npackages; i++)
+ − 687 if (strcmp (package[i].name, pkg) == 0)
+ − 688 {
+ − 689 int t;
+ − 690 extra[i].installed_file = inst;
+ − 691 extra[i].installed_size = instsz;
+ − 692
+ − 693 for (t=0; t<NTRUST; t++)
+ − 694 if (package[i].info[t].install
+ − 695 && strcmp (base (package[i].info[t].install), base (inst)) == 0)
+ − 696 {
+ − 697 extra[i].which_is_installed = t;
+ − 698 extra[i].installed_ver = package[i].info[t].version;
+ − 699 break;
+ − 700 }
+ − 701
+ − 702 if (extra[i].installed_ver == 0) /* still */
+ − 703 {
+ − 704 char *v, *d;
+ − 705 for (v=base (inst); *v; v++)
+ − 706 if (*v == '-' && isdigit(v[1]))
+ − 707 {
+ − 708 v++;
+ − 709 break;
+ − 710 }
+ − 711 if (!v)
+ − 712 v = inst;
+ − 713 for (d=v; *d; d++)
+ − 714 if (strncmp (d, ".tar", 4) == 0
+ − 715 || strncmp (d, "-pkg", 4) == 0)
+ − 716 {
+ − 717 *d = 0;
+ − 718 break;
+ − 719 }
+ − 720 if (v[0])
+ − 721 extra[i].installed_ver = strdup (v);
+ − 722 else
+ − 723 extra[i].installed_ver = "0";
+ − 724 }
+ − 725 break;
+ − 726 }
+ − 727 }
+ − 728 fclose (db);
+ − 729 }
+ − 730
+ − 731 int CDECL
+ − 732 package_sort (const void *va, const void *vb)
+ − 733 {
+ − 734 Package *a = (Package *)va;
+ − 735 Package *b = (Package *)vb;
+ − 736 return strcmp (a->name, b->name);
+ − 737 }
+ − 738
+ − 739 void
+ − 740 do_choose (HINSTANCE h)
+ − 741 {
+ − 742 int rv, i;
+ − 743
+ − 744 qsort (package, npackages, sizeof (package[0]), package_sort);
+ − 745
+ − 746 nextbutton = 0;
+ − 747 bm_spin = LoadImage (h, MAKEINTRESOURCE (IDB_SPIN), IMAGE_BITMAP, 0, 0, 0);
+ − 748 bm_rtarrow = LoadImage (h, MAKEINTRESOURCE (IDB_RTARROW), IMAGE_BITMAP, 0, 0, 0);
+ − 749
+ − 750 bm_checkyes = LoadImage (h, MAKEINTRESOURCE (IDB_CHECK_YES), IMAGE_BITMAP, 0, 0, 0);
+ − 751 bm_checkno = LoadImage (h, MAKEINTRESOURCE (IDB_CHECK_NO), IMAGE_BITMAP, 0, 0, 0);
+ − 752 bm_checkna = LoadImage (h, MAKEINTRESOURCE (IDB_CHECK_NA), IMAGE_BITMAP, 0, 0, 0);
+ − 753
+ − 754 extra = (ExtraPackageInfo *) malloc (npackages * sizeof (ExtraPackageInfo));
+ − 755 memset (extra, 0, npackages * sizeof (ExtraPackageInfo));
+ − 756 for (i=0; i<npackages; i++)
+ − 757 extra[i].which_is_installed = -1;
+ − 758
+ − 759 register_windows (h);
+ − 760
+ − 761 if (source == IDC_SOURCE_DOWNLOAD)
+ − 762 scan_downloaded_files ();
+ − 763 else
+ − 764 read_installed_db ();
+ − 765 build_labels ();
+ − 766
+ − 767 rv = DialogBox (h, MAKEINTRESOURCE (IDD_CHOOSE), 0, dialog_proc);
+ − 768 if (rv == -1)
+ − 769 fatal (IDS_DIALOG_FAILED);
+ − 770
+ − 771 for (i=0; i<npackages; i++)
+ − 772 {
+ − 773 switch (extra[i].chooser[extra[i].pick].trust)
+ − 774 {
+ − 775 case TRUST_PREV:
+ − 776 case TRUST_CURR:
+ − 777 case TRUST_TEST:
+ − 778 if (extra[i].installed_file)
+ − 779 package[i].action = ACTION_UPGRADE;
+ − 780 else
+ − 781 package[i].action = ACTION_NEW;
+ − 782 package[i].trust = extra[i].chooser[extra[i].pick].trust;
+ − 783 // pick up the actual core package to install
+ − 784 if (package[i].type == TY_CYGWIN || package[i].type == TY_NATIVE
+ − 785 && xemacs_package == 0)
+ − 786 xemacs_package = &package[i];
+ − 787 break;
+ − 788
+ − 789 case TRUST_UNINSTALL:
+ − 790 package[i].action = ACTION_UNINSTALL;
+ − 791 break;
+ − 792
+ − 793 case TRUST_KEEP:
+ − 794 case TRUST_NONE:
+ − 795 default:
+ − 796 package[i].action = ACTION_SAME;
+ − 797 break;
+ − 798 }
+ − 799 }
+ − 800
+ − 801 log (LOG_BABBLE, "Chooser results...");
+ − 802 for (i=0; i<npackages; i++)
+ − 803 {
+ − 804 static char *infos[] = {"prev", "curr", "test"};
+ − 805 const char *trust = ((package[i].trust == TRUST_PREV) ? "prev"
+ − 806 : (package[i].trust == TRUST_CURR) ? "curr"
+ − 807 : (package[i].trust == TRUST_TEST) ? "test"
+ − 808 : "unknown");
+ − 809 const char *action = ((package[i].action == ACTION_UNKNOWN) ? "unknown"
+ − 810 : (package[i].action == ACTION_SAME) ? "same"
+ − 811 : (package[i].action == ACTION_NEW) ? "new"
+ − 812 : (package[i].action == ACTION_UPGRADE) ? "upgrade"
+ − 813 : (package[i].action == ACTION_UNINSTALL) ? "uninstall"
+ − 814 : (package[i].action == ACTION_ERROR) ? "error"
+ − 815 : "unknown");
+ − 816
+ − 817 log (LOG_BABBLE, "[%s] action=%s trust=%s src? %s", package[i].name, action, trust,
+ − 818 package[i].srcaction == SRCACTION_NO ? "no" : "yes");
+ − 819 for (int t=0; t<NTRUST; t++)
+ − 820 {
+ − 821 if (package[i].info[t].install)
+ − 822 log (LOG_BABBLE, "[%s] ver %s inst %s %d src %s %d",
+ − 823 infos[t],
+ − 824 package[i].info[t].version ? package[i].info[t].version : "(none)",
+ − 825 package[i].info[t].install ? package[i].info[t].install : "(none)",
+ − 826 package[i].info[t].install_size,
+ − 827 package[i].info[t].source ? package[i].info[t].source : "(none)",
+ − 828 package[i].info[t].source_size);
+ − 829 }
+ − 830 }
+ − 831 }