Changeset 1469 for trunk/dll/comp.c


Ignore:
Timestamp:
Sep 28, 2009, 6:21:02 PM (16 years ago)
Author:
Steven Levine
Message:

Enhance compare directories - support AND'ed selections, rework CompSelect for size and speed,
allow fast cancel, drop unused reset logic, more context menu items

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/dll/comp.c

    r1444 r1469  
    6868  28 Jun 09 GKY Added AddBackslashToPath() to remove repeatative code.
    6969  13 Jul 09 SHL Sync with renames
     70  26 Sep 09 SHL Don't hide if nothing selected
     71  27 Sep 09 SHL Support AND'ed selections
     72  27 Sep 09 SHL Rework CompSelect for size and speed
     73  27 Sep 09 SHL Allow fast cancel
     74  27 Sep 09 SHL Drop unused reset logic
    7075
    7176***********************************************************************/
     
    7681#include <io.h>
    7782#include <ctype.h>
    78 // #include <process.h>                 // _endthread
    7983
    8084#define INCL_DOS
     
    125129#include "fortify.h"                    // 06 May 08 SHL added
    126130#include "excputil.h"                   // xbeginthread
    127 #include "info.h"                       // driveflags
     131#include "info.h"                       // driveflags
    128132
    129133typedef struct
     
    141145BOOL fSelectedAlways;
    142146
    143 //=== SnapShot() Write directory tree to file and recurse if requested ===
     147/**
     148 * Write directory tree to snapshot file; recurse if requested
     149 */
    144150
    145151static VOID SnapShot(char *path, FILE *fp, BOOL recurse)
     
    149155  HDIR hdir = HDIR_CREATE;
    150156  ULONG ulFindCnt;
    151   CHAR  szCmmaFmtFileSize[81], szDate[DATE_BUF_BYTES];
     157  CHAR szCmmaFmtFileSize[81], szDate[DATE_BUF_BYTES];
    152158
    153159  // 13 Aug 07 SHL fimxe to use FileToGet
     
    169175        do {
    170176          strcpy(enddir, pffb->achName);
    171           if (!(pffb->attrFile & FILE_DIRECTORY)) {
    172             CommaFmtULL(szCmmaFmtFileSize,
    173                         sizeof(szCmmaFmtFileSize), pffb->cbFile, ' ');
    174             FDateFormat(szDate, pffb->fdateLastWrite);
     177          if (!(pffb->attrFile & FILE_DIRECTORY)) {
     178            CommaFmtULL(szCmmaFmtFileSize,
     179                        sizeof(szCmmaFmtFileSize), pffb->cbFile, ' ');
     180            FDateFormat(szDate, pffb->fdateLastWrite);
    175181            fprintf(fp,
    176182                    "\"%s\",%u,%s,%s,%02u%s%02u%s%02u,%lu,%lu,N\n",
     
    179185                    szCmmaFmtFileSize,
    180186                    szDate,
    181                     pffb->ftimeLastWrite.hours,
    182                     TimeSeparator,
    183                     pffb->ftimeLastWrite.minutes,
    184                     TimeSeparator,
     187                    pffb->ftimeLastWrite.hours,
     188                    TimeSeparator,
     189                    pffb->ftimeLastWrite.minutes,
     190                    TimeSeparator,
    185191                    pffb->ftimeLastWrite.twosecs,
    186192                    pffb->attrFile,
    187                     pffb->cbList > 4 ? pffb->cbList / 2 : 0);
    188           }
     193                    pffb->cbList > 4 ? pffb->cbList / 2 : 0);
     194          }
    189195          // Skip . and ..
    190196          else if (recurse &&
     
    204210}
    205211
    206 //=== StartSnap() Write directory tree to snapshot file ===
    207 
    208 static VOID StartSnap(VOID *pargs)
     212/**
     213 * Write snapshot file thread
     214 * Write directory tree to snapshot file
     215 */
     216
     217static VOID StartSnapThread(VOID *pargs)
    209218{
    210219  SNAPSTUFF *sf = (SNAPSTUFF *)pargs;
     
    236245}
    237246
    238 //=== CompareFilesThread() Compare files and update container select flags ===
     247/**
     248 * Compare files thread
     249 * Scan files and update container select flags
     250 */
    239251
    240252static VOID CompareFilesThread(VOID *args)
     
    374386}
    375387
    376 //=== CFileDlgProc() Select directories to compare dialog procedure ===
     388/**
     389 * Select directories to compare dialog procedure
     390 */
    377391
    378392MRESULT EXPENTRY CFileDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
     
    441455}
    442456
    443 //=== ActionCnrThread() Do requested action on container contents ===
     457/**
     458 * Action Thread
     459 * Do requested action on container contents
     460 */
    444461
    445462static VOID ActionCnrThread(VOID *args)
     
    515532
    516533      while (pciS && (INT)pciS != -1 && pciD && (INT)pciD != -1) {
     534
     535        if (cmp->cmp->stop)
     536          break;                        // 27 Sep 09 SHL
    517537
    518538        pciNextS = WinSendMsg(hwndCnrS, CM_QUERYRECORD, MPFROMP(pciS),
     
    710730                  WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
    711731                             MPFROM2SHORT(FALSE, CRA_SELECTED));
    712                 // 12 Jan 08 SHL
    713                 if (pciD->pszFileName == NullStr) {
     732                if (~pciD->flags & CNRITEM_EXISTS) {
    714733                  if (hwndCnrD == WinWindowFromID(cmp->hwnd, COMP_LEFTDIR))
    715                     cmp->totalleft++;
     734                    cmp->cmp->totalleft++;
    716735                  else
    717                     cmp->totalright++;
     736                    cmp->cmp->totalright++;
    718737                }
    719738                FreeCnrItemData(pciD);
     
    772791    }
    773792    PostMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPFROMLONG(1), MPVOID);
    774     // PostMsg(cmp->hwnd, WM_COMMAND, MPFROM2SHORT(IDM_DESELECTALL, 0), MPVOID);        // 18 Jan 08 SHL we can count now
    775793    DecrThreadUsage();
    776794    free(cmp);
     
    784802}
    785803
    786 VOID CompSelect(HWND hwndCnrS, HWND hwndCnrD, HWND hwnd, INT action, BOOL reset);
    787 
    788 //=== SelectCnrsThread() Update container selection flags thread ===
     804static VOID CompSelect(HWND hwndCnrS, HWND hwndCnrD, HWND hwnd, INT action, USHORT shiftstate, BOOL *stop);
     805
     806/**
     807 * Update container selection flags thread
     808 */
    789809
    790810static VOID SelectCnrsThread(VOID *args)
     
    823843
    824844      default:
    825         // 08 Feb 09 SHL fixme to support Ctrl-click for ANDed select
    826         // 13 Jan 08 SHL fixme to decide if cmp->reset can ever get set
    827         // if not lots of code can disappear
    828         if (cmp->reset)
    829           DbgMsg(pszSrcFile, __LINE__, "cmp->reset is TRUE");
    830845        CompSelect(WinWindowFromID(cmp->hwnd, COMP_LEFTDIR),
    831846                   WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR),
    832847                   cmp->hwnd,
    833848                   cmp->action,
    834                    cmp->reset);
     849                   cmp->shiftstate,
     850                   &cmp->cmp->stop);
    835851        break;
    836852      }
     
    851867
    852868/**
     869 * Set item selections for CompSelect
     870 */
     871
     872static VOID CompSelectSetSelects(PCNRITEM pciS, PCNRITEM pciD, BOOL matchS, BOOL matchD, BOOL wantAnd);
     873
     874static VOID CompSelectSetSelects(PCNRITEM pciS, PCNRITEM pciD, BOOL matchS, BOOL matchD, BOOL wantAnd)
     875{
     876  ULONG oldSel;
     877  ULONG newSel;
     878
     879  oldSel = pciS->rc.flRecordAttr & CRA_SELECTED;
     880  newSel = matchS ? (wantAnd ? oldSel : CRA_SELECTED) : (wantAnd ? 0 : oldSel);
     881  if ((pciS->rc.flRecordAttr & CRA_SELECTED) != newSel)
     882    WinSendMsg(pciS->hwndCnr, CM_SETRECORDEMPHASIS, MPFROMP(pciS),
     883               MPFROM2SHORT(newSel ? TRUE : FALSE, CRA_SELECTED));
     884
     885  oldSel = pciD->rc.flRecordAttr & CRA_SELECTED;
     886  newSel = matchD ? (wantAnd ? oldSel : CRA_SELECTED) : (wantAnd ? 0 : oldSel);
     887  if ((pciD->rc.flRecordAttr & CRA_SELECTED) != newSel) {
     888    WinSendMsg(pciD->hwndCnr, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
     889               MPFROM2SHORT(newSel ? TRUE : FALSE, CRA_SELECTED));
     890  }
     891}
     892
     893/**
     894 * Clear item selections for CompSelect
     895 */
     896
     897static BOOL CompSelectClearSelects(PCNRITEM pciS, PCNRITEM pciD, BOOL matchS, BOOL matchD);
     898
     899static BOOL CompSelectClearSelects(PCNRITEM pciS, PCNRITEM pciD, BOOL matchS, BOOL matchD)
     900{
     901  BOOL changed;
     902
     903  if ((pciS->rc.flRecordAttr & CRA_SELECTED) && matchS) {
     904    WinSendMsg(pciS->hwndCnr, CM_SETRECORDEMPHASIS, MPFROMP(pciS),
     905               MPFROM2SHORT(FALSE, CRA_SELECTED));
     906    changed = TRUE;
     907  }
     908  else
     909    changed = FALSE;
     910
     911  if ((pciD->rc.flRecordAttr & CRA_SELECTED) && matchD) {
     912    WinSendMsg(pciD->hwndCnr, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
     913               MPFROM2SHORT(FALSE, CRA_SELECTED));
     914    changed = TRUE;
     915  }
     916
     917  return changed;
     918}
     919
     920/**
    853921 * Do select actions for compare directories containers
    854922 * @param action is select mode
    855  * @param reset requests flags by regenerated
    856923 */
    857924
    858 VOID CompSelect(HWND hwndCnrS, HWND hwndCnrD, HWND hwnd, INT action, BOOL reset)
     925static VOID CompSelect(HWND hwndCnrS, HWND hwndCnrD, HWND hwnd, INT action, USHORT shiftstate, BOOL *stop)
    859926{
    860   PCNRITEM pciS, pciD, *pciSa = NULL, *pciDa = NULL;
     927  PCNRITEM pciS;
     928  PCNRITEM pciD;
     929  PCNRITEM *pciSa = NULL;
     930  PCNRITEM *pciDa = NULL;
    861931  CNRINFO cnri;
    862932  BOOL slow = FALSE;
    863   UINT x, numD, numS;
    864   INT ret = 0;
     933  UINT x;
     934  UINT numD;
     935  UINT numS;
    865936  ITIMER_DESC itdSleep = { 0 };
    866937  BOOL fUpdateHideButton = FALSE;
     938  BOOL wantAnd = (shiftstate & (KC_SHIFT | KC_ALT | KC_CTRL)) == KC_CTRL;
     939  BOOL matched;
    867940
    868941  if (!hwndCnrS || !hwndCnrD) {
     
    904977
    905978  pciD = (PCNRITEM)WinSendMsg(hwndCnrD, CM_QUERYRECORD, MPVOID,
    906                                MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
     979                              MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
    907980  x = 0;
    908981  while (pciD && (INT)pciD != -1 && x < numD) {
    909     if (reset)
    910       pciD->flags = 0;
    911982    pciDa[x] = pciD;
    912983    x++;
     
    920991
    921992  if (numD != x) {
    922     // Something out of sync - fixme to document why
     993    // Something out of sync - fixme to document why slow logic needed
    923994    if (!slow) {
    924995      slow = TRUE;
     
    9351006  x = 0;
    9361007  while (pciS && (INT)pciS != -1 && x < numS) {
    937     if (reset)
    938       pciS->flags = 0;
    9391008    pciSa[x] = pciS;
    9401009    x++;
     
    9581027  }
    9591028
    960   if (reset) {
    961     // Update flags for files that exist on both sides
    962     for (x = 0; x < numS; x++) {
    963 
    964       if (!*pciSa[x]->pszFileName || !*pciDa[x]->pszFileName) {
    965         // 12 Jan 08 SHL clear flags
    966         pciSa[x]->flags = 0;            // File exists on one side only
    967         pciDa[x]->flags = 0;
    968         continue;
    969       }
    970 
    971       pciSa[x]->flags |= CNRITEM_EXISTS;        // File exists on both sides
    972       pciDa[x]->flags |= CNRITEM_EXISTS;
    973       if (pciSa[x]->cbFile + pciSa[x]->easize >
    974           pciDa[x]->cbFile + pciDa[x]->easize) {
    975         pciSa[x]->flags |= CNRITEM_LARGER;
    976         pciDa[x]->flags |= CNRITEM_SMALLER;
    977       }
    978       else if (pciSa[x]->cbFile + pciSa[x]->easize <
    979                pciDa[x]->cbFile + pciDa[x]->easize) {
    980         pciSa[x]->flags |= CNRITEM_SMALLER;
    981         pciDa[x]->flags |= CNRITEM_LARGER;
    982       }
    983       ret = TestCDates(&pciDa[x]->date, &pciDa[x]->time,
    984                        &pciSa[x]->date, &pciSa[x]->time);
    985       if (ret == 1)
    986         /* 13 Jan 08 SHL fixme to be gone?
    987           ((pciSa[x]->date.year > pciDa[x]->date.year) ? TRUE :
    988           (pciSa[x]->date.year < pciDa[x]->date.year) ? FALSE :
    989           (pciSa[x]->date.month > pciDa[x]->date.month) ? TRUE :
    990           (pciSa[x]->date.month < pciDa[x]->date.month) ? FALSE :
    991           (pciSa[x]->date.day > pciDa[x]->date.day) ? TRUE :
    992           (pciSa[x]->date.day < pciDa[x]->date.day) ? FALSE :
    993           (pciSa[x]->time.hours > pciDa[x]->time.hours) ? TRUE :
    994           (pciSa[x]->time.hours < pciDa[x]->time.hours) ? FALSE :
    995           (pciSa[x]->time.minutes > pciDa[x]->time.minutes) ? TRUE :
    996           (pciSa[x]->time.minutes < pciDa[x]->time.minutes) ? FALSE :
    997           (pciSa[x]->time.seconds > pciDa[x]->time.seconds) ? TRUE :
    998           (pciSa[x]->time.seconds < pciDa[x]->time.seconds) ? FALSE : FALSE)
    999         */
    1000       {
    1001         pciSa[x]->flags |= CNRITEM_NEWER;
    1002         pciDa[x]->flags |= CNRITEM_OLDER;
    1003       }
    1004       else if (ret == -1)
    1005         /* 13 Jan 08 SHL fixme to be gone?
    1006           ((pciSa[x]->date.year < pciDa[x]->date.year) ? TRUE :
    1007           (pciSa[x]->date.year > pciDa[x]->date.year) ? FALSE :
    1008           (pciSa[x]->date.month < pciDa[x]->date.month) ? TRUE :
    1009           (pciSa[x]->date.month > pciDa[x]->date.month) ? FALSE :
    1010           (pciSa[x]->date.day < pciDa[x]->date.day) ? TRUE :
    1011           (pciSa[x]->date.day > pciDa[x]->date.day) ? FALSE :
    1012           (pciSa[x]->time.hours < pciDa[x]->time.hours) ? TRUE :
    1013           (pciSa[x]->time.hours > pciDa[x]->time.hours) ? FALSE :
    1014           (pciSa[x]->time.minutes < pciDa[x]->time.minutes) ? TRUE :
    1015           (pciSa[x]->time.minutes > pciDa[x]->time.minutes) ? FALSE :
    1016           (pciSa[x]->time.seconds < pciDa[x]->time.seconds) ? TRUE :
    1017           (pciSa[x]->time.seconds > pciDa[x]->time.seconds) ? FALSE :
    1018           FALSE)
    1019         */
    1020       {
    1021         pciSa[x]->flags |= CNRITEM_OLDER;
    1022         pciDa[x]->flags |= CNRITEM_NEWER;
    1023       }
    1024       SleepIfNeeded(&itdSleep, 0);
    1025     } // for
    1026   } // if reset
    1027 
    10281029  switch (action) {
    10291030  case IDM_SELECTIDENTICAL:
     1031    // Same Date/size
    10301032    for (x = 0; x < numS; x++) {
    1031       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED &&
    1032           pciSa[x]->flags & CNRITEM_EXISTS &&
    1033           ~pciSa[x]->flags & CNRITEM_SMALLER &&
    1034           ~pciSa[x]->flags & CNRITEM_LARGER &&
    1035           ~pciSa[x]->flags & CNRITEM_NEWER &&
    1036           ~pciSa[x]->flags & CNRITEM_OLDER) {
    1037         if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1038           WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1039                      MPFROM2SHORT(TRUE, CRA_SELECTED));
    1040         if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1041           WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1042                      MPFROM2SHORT(TRUE, CRA_SELECTED));
     1033      pciS = pciSa[x];
     1034      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1035        matched = pciS->flags & CNRITEM_EXISTS &&
     1036                  ~pciS->flags & CNRITEM_SMALLER &&
     1037                  ~pciS->flags & CNRITEM_LARGER &&
     1038                  ~pciS->flags & CNRITEM_NEWER &&
     1039                  ~pciS->flags & CNRITEM_OLDER;
     1040        CompSelectSetSelects(pciS, pciDa[x], matched, matched, wantAnd);
    10431041      }
    10441042      SleepIfNeeded(&itdSleep, 0);
     
    10471045
    10481046  case IDM_SELECTSAME:
     1047    // Same Size
    10491048    for (x = 0; x < numS; x++) {
    1050       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED &&
    1051           pciSa[x]->flags & CNRITEM_EXISTS &&
    1052           ~pciSa[x]->flags & CNRITEM_SMALLER &&
    1053           ~pciSa[x]->flags & CNRITEM_LARGER) {
    1054         if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1055           WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1056                      MPFROM2SHORT(TRUE, CRA_SELECTED));
    1057         if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1058           WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1059                      MPFROM2SHORT(TRUE, CRA_SELECTED));
     1049      pciS = pciSa[x];
     1050      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1051        matched = pciS->flags & CNRITEM_EXISTS &&
     1052                  ~pciS->flags & CNRITEM_SMALLER &&
     1053                  ~pciS->flags & CNRITEM_LARGER;
     1054        CompSelectSetSelects(pciS, pciDa[x], matched, matched, wantAnd);
    10601055      }
    10611056      SleepIfNeeded(&itdSleep, 0);
     
    10641059
    10651060  case IDM_SELECTSAMECONTENT:
    1066     for (x = 0; x < numS; x++) {
    1067       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED &&
    1068           pciSa[x]->flags & CNRITEM_EXISTS)
    1069       {
    1070         FILE *fp1 = NULL;
    1071         FILE *fp2 = NULL;
    1072         BOOL gotMatch = FALSE;
    1073         UINT errLineNo = 0;
    1074         UINT compErrno = 0;
    1075         CHAR buf1[1024];
    1076         CHAR buf2[1024];
    1077         HAB hab = WinQueryAnchorBlock(hwndCnrS);
    1078 
    1079         if (!*pciSa[x]->pszFileName ||
    1080             !*pciDa[x]->pszFileName) {
    1081           Runtime_Error(pszSrcFile, __LINE__,
    1082                         "CNRITEM_EXISTS set with null file name for index %u", x);
    1083           break;
    1084         }
    1085 
    1086         fp1 = _fsopen(pciSa[x]->pszFileName, "rb", SH_DENYNO);
    1087         if (!fp1) {
    1088           errLineNo = __LINE__;
    1089           compErrno = errno;
    1090         }
    1091         else {
    1092           fp2 = _fsopen(pciDa[x]->pszFileName, "rb", SH_DENYNO);
    1093           if (!fp2) {
     1061    for (x = 0; x < numS && !*stop; x++) {
     1062
     1063      pciS = pciSa[x];
     1064      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1065        matched = FALSE;
     1066        pciD = pciDa[x];
     1067        if (pciS->flags & CNRITEM_EXISTS) {
     1068          FILE *fp1 = NULL;
     1069          FILE *fp2 = NULL;
     1070          UINT errLineNo = 0;
     1071          UINT compErrno = 0;
     1072          CHAR buf1[1024];
     1073          CHAR buf2[1024];
     1074          HAB hab = WinQueryAnchorBlock(hwndCnrS);
     1075
     1076          if (!*pciS->pszFileName ||
     1077              !*pciD->pszFileName) {
     1078            Runtime_Error(pszSrcFile, __LINE__,
     1079                          "CNRITEM_EXISTS set with null file name for index %u", x);
     1080            break;
     1081          }
     1082
     1083          fp1 = _fsopen(pciS->pszFileName, "rb", SH_DENYNO);
     1084          if (!fp1) {
    10941085            errLineNo = __LINE__;
    10951086            compErrno = errno;
    10961087          }
    10971088          else {
    1098             size_t len1 = filelength(fileno(fp1));
    1099             size_t len2 = filelength(fileno(fp2));
    1100 
    1101             if (len1 == len2) {
    1102               setbuf(fp1, NULL);
    1103               setbuf(fp2, NULL);
    1104               while (WinIsWindow(hab, hwndCnrS)) {
    1105                 size_t numread1 = fread(buf1, 1, 1024, fp1);
    1106                 size_t numread2 = fread(buf2, 1, 1024, fp2);
    1107 
    1108                 if (!numread1 || !numread2 || numread1 != numread2) {
    1109                   if (ferror(fp1) || ferror(fp2)) {
    1110                     errLineNo = __LINE__;
    1111                     compErrno = errno;
     1089            fp2 = _fsopen(pciD->pszFileName, "rb", SH_DENYNO);
     1090            if (!fp2) {
     1091              errLineNo = __LINE__;
     1092              compErrno = errno;
     1093            }
     1094            else {
     1095              size_t len1 = filelength(fileno(fp1));
     1096              size_t len2 = filelength(fileno(fp2));
     1097              if (len1 == len2) {
     1098                setbuf(fp1, NULL);
     1099                setbuf(fp2, NULL);
     1100                while (WinIsWindow(hab, hwndCnrS)) {
     1101                  size_t numread1 = fread(buf1, 1, 1024, fp1);
     1102                  size_t numread2 = fread(buf2, 1, 1024, fp2);
     1103
     1104                  if (!numread1 || !numread2 || numread1 != numread2) {
     1105                    if (ferror(fp1) || ferror(fp2)) {
     1106                      errLineNo = __LINE__;
     1107                      compErrno = errno;
     1108                    }
     1109                    else if (feof(fp1) && feof(fp2))
     1110                      matched = TRUE;
     1111                    break;
    11121112                  }
    1113                   else if (feof(fp1) && feof(fp2))
    1114                     gotMatch = TRUE;
    1115                   break;
    1116                 }
    1117                 else if (memcmp(buf1, buf2, numread1))
    1118                   break;
    1119               } // while
    1120             } // same len
    1121           }
    1122         }
    1123 
    1124         if (fp1)
    1125           fclose(fp1);
    1126 
    1127         if (fp2)
    1128           fclose(fp2);
    1129 
    1130         if (errLineNo) {
    1131           Runtime_Error(pszSrcFile, errLineNo,
    1132                         "error %d while comparing", compErrno);
    1133         }
    1134 
    1135         if (gotMatch) {
    1136           if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1137             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1138                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1139           if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1140             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1141                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1142         }
    1143       }
     1113                  else if (memcmp(buf1, buf2, numread1))
     1114                    break;
     1115                }       // while
     1116              } // same len
     1117            } // if open ok
     1118          } // if open ok
     1119          if (fp1)
     1120            fclose(fp1);
     1121          if (fp2)
     1122            fclose(fp2);
     1123
     1124          if (errLineNo) {
     1125            Runtime_Error(pszSrcFile, errLineNo,
     1126                          "error %d while comparing", compErrno);
     1127          }
     1128        } // if exists
     1129        CompSelectSetSelects(pciS, pciD, matched, matched, wantAnd);
     1130      } // if not filtered
    11441131      SleepIfNeeded(&itdSleep, 0);
    11451132    } // for
     
    11481135  case IDM_SELECTBOTH:
    11491136    for (x = 0; x < numS; x++) {
    1150       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED &&
    1151           pciSa[x]->flags & CNRITEM_EXISTS) {
    1152         if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1153           WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1154                      MPFROM2SHORT(TRUE, CRA_SELECTED));
    1155         if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1156           WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1157                      MPFROM2SHORT(TRUE, CRA_SELECTED));
     1137      pciS = pciSa[x];
     1138      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1139        pciD = pciDa[x];
     1140        matched = pciS->flags & CNRITEM_EXISTS;
     1141        CompSelectSetSelects(pciS, pciD, matched, matched, wantAnd);
    11581142      }
    11591143      SleepIfNeeded(&itdSleep, 0);
     
    11631147  case IDM_SELECTONE:
    11641148    for (x = 0; x < numS; x++) {
    1165       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED &&
    1166           ~pciSa[x]->flags & CNRITEM_EXISTS) {
    1167         if (*pciSa[x]->pszFileName) {
    1168           if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1169             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1170                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1171           }
    1172         }
    1173         else if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1174           WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1175                      MPFROM2SHORT(TRUE, CRA_SELECTED));
    1176         }
     1149      pciS = pciSa[x];
     1150      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1151        pciD = pciDa[x];
     1152        CompSelectSetSelects(pciS,
     1153                             pciD,
     1154                             ~pciS->flags & CNRITEM_EXISTS && *pciS->pszFileName,
     1155                             ~pciD->flags & CNRITEM_EXISTS && *pciD->pszFileName,
     1156                             wantAnd);
    11771157      }
    11781158      SleepIfNeeded(&itdSleep, 0);
     
    11821162  case IDM_SELECTBIGGER:
    11831163    for (x = 0; x < numS; x++) {
    1184       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1185         if (pciSa[x]->flags & CNRITEM_LARGER) {
    1186           if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1187             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1188                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1189         }
    1190         else if (pciDa[x]->flags & CNRITEM_LARGER) {
    1191           if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1192             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1193                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1194         }
     1164      pciS = pciSa[x];
     1165      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1166        pciD = pciDa[x];
     1167        CompSelectSetSelects(pciS,
     1168                             pciD,
     1169                             pciS->flags & CNRITEM_LARGER,
     1170                             pciD->flags & CNRITEM_LARGER,
     1171                             wantAnd);
    11951172      }
    11961173      SleepIfNeeded(&itdSleep, 0);
     
    12001177  case IDM_SELECTSMALLER:
    12011178    for (x = 0; x < numS; x++) {
    1202       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1203         if (pciSa[x]->flags & CNRITEM_SMALLER) {
    1204           if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1205             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1206                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1207         }
    1208         else if (pciDa[x]->flags & CNRITEM_SMALLER) {
    1209           if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1210             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1211                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1212         }
     1179      pciS = pciSa[x];
     1180      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1181        pciD = pciDa[x];
     1182        CompSelectSetSelects(pciS,
     1183                             pciD,
     1184                             pciS->flags & CNRITEM_SMALLER,
     1185                             pciD->flags & CNRITEM_SMALLER,
     1186                             wantAnd);
    12131187      }
    12141188      SleepIfNeeded(&itdSleep, 0);
     
    12181192  case IDM_SELECTNEWER:
    12191193    for (x = 0; x < numS; x++) {
    1220       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1221         if (pciSa[x]->flags & CNRITEM_NEWER) {
    1222           if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1223             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1224                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1225         }
    1226         else if (pciDa[x]->flags & CNRITEM_NEWER) {
    1227           if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1228             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1229                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1230         }
     1194      pciS = pciSa[x];
     1195      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1196        pciD = pciDa[x];
     1197        CompSelectSetSelects(pciS,
     1198                             pciD,
     1199                             pciS->flags & CNRITEM_NEWER,
     1200                             pciD->flags & CNRITEM_NEWER,
     1201                             wantAnd);
    12311202      }
    12321203      SleepIfNeeded(&itdSleep, 0);
     
    12361207  case IDM_SELECTOLDER:
    12371208    for (x = 0; x < numS; x++) {
    1238       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1239         if (pciSa[x]->flags & CNRITEM_OLDER) {
    1240           if (~pciSa[x]->rc.flRecordAttr & CRA_SELECTED)
    1241             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1242                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1243         }
    1244         else if (pciDa[x]->flags & CNRITEM_OLDER) {
    1245           if (~pciDa[x]->rc.flRecordAttr & CRA_SELECTED)
    1246             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1247                        MPFROM2SHORT(TRUE, CRA_SELECTED));
    1248         }
     1209      pciS = pciSa[x];
     1210      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1211        pciD = pciDa[x];
     1212        CompSelectSetSelects(pciS,
     1213                             pciD,
     1214                             pciS->flags & CNRITEM_OLDER,
     1215                             pciD->flags & CNRITEM_OLDER,
     1216                             wantAnd);
    12491217      }
    12501218      SleepIfNeeded(&itdSleep, 0);
     
    12541222  case IDM_DESELECTBOTH:
    12551223    for (x = 0; x < numS; x++) {
    1256       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED &&
    1257           pciSa[x]->flags & CNRITEM_EXISTS) {
    1258         if (pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1259           WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1260                      MPFROM2SHORT(FALSE, CRA_SELECTED));
     1224      pciS = pciSa[x];
     1225      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1226        matched = pciS->flags & CNRITEM_EXISTS;
     1227        if (CompSelectClearSelects(pciS, pciDa[x], matched, matched))
    12611228          fUpdateHideButton = TRUE;
    1262         }
    1263         if (pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1264           WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1265                      MPFROM2SHORT(FALSE, CRA_SELECTED));
    1266           fUpdateHideButton = TRUE;
    1267         }
    12681229      }
    12691230      SleepIfNeeded(&itdSleep, 0);
     
    12731234  case IDM_DESELECTONE:
    12741235    for (x = 0; x < numS; x++) {
    1275       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1276         if (~pciSa[x]->flags & CNRITEM_EXISTS) {
    1277           if (*pciSa[x]->pszFileName) {
    1278             if (pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1279               WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1280                          MPFROM2SHORT(FALSE, CRA_SELECTED));
    1281               fUpdateHideButton = TRUE;
    1282             }
    1283           }
    1284           else if (pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1285             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1286                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1287             fUpdateHideButton = TRUE;
    1288           }
     1236      pciS = pciSa[x];
     1237      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1238        pciD = pciDa[x];
     1239        if (CompSelectClearSelects(pciS,
     1240                                   pciD,
     1241                                   ~pciS->flags & CNRITEM_EXISTS && *pciS->pszFileName,
     1242                                   ~pciD->flags & CNRITEM_EXISTS && *pciD->pszFileName)) {
     1243          fUpdateHideButton = TRUE;
    12891244        }
    12901245      }
     
    12951250  case IDM_DESELECTBIGGER:
    12961251    for (x = 0; x < numS; x++) {
    1297       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1298         if (pciSa[x]->flags & CNRITEM_LARGER) {
    1299           if (pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1300             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1301                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1302             fUpdateHideButton = TRUE;
    1303           }
    1304         }
    1305         else if (pciDa[x]->flags & CNRITEM_LARGER) {
    1306           if (pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1307             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1308                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1309             fUpdateHideButton = TRUE;
    1310           }
     1252      pciS = pciSa[x];
     1253      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1254        pciD = pciDa[x];
     1255        if (CompSelectClearSelects(pciS,
     1256                                   pciD,
     1257                                   pciS->flags & CNRITEM_LARGER,
     1258                                   pciD->flags & CNRITEM_LARGER)) {
     1259          fUpdateHideButton = TRUE;
    13111260        }
    13121261      }
     
    13171266  case IDM_DESELECTSMALLER:
    13181267    for (x = 0; x < numS; x++) {
    1319       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1320         if (pciSa[x]->flags & CNRITEM_SMALLER) {
    1321           if (pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1322             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1323                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1324             fUpdateHideButton = TRUE;
    1325           }
    1326         }
    1327         else if (pciDa[x]->flags & CNRITEM_SMALLER) {
    1328           if (pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1329             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1330                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1331             fUpdateHideButton = TRUE;
    1332           }
     1268      pciS = pciSa[x];
     1269      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1270        pciD = pciDa[x];
     1271        if (CompSelectClearSelects(pciS,
     1272                                   pciD,
     1273                                   pciS->flags & CNRITEM_SMALLER,
     1274                                   pciD->flags & CNRITEM_SMALLER)) {
     1275          fUpdateHideButton = TRUE;
    13331276        }
    13341277      }
     
    13391282  case IDM_DESELECTNEWER:
    13401283    for (x = 0; x < numS; x++) {
    1341       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1342         if (pciSa[x]->flags & CNRITEM_NEWER) {
    1343           if (pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1344             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1345                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1346             fUpdateHideButton = TRUE;
    1347           }
    1348         }
    1349         else if (pciDa[x]->flags & CNRITEM_NEWER) {
    1350           if (pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1351             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1352                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1353             fUpdateHideButton = TRUE;
    1354           }
     1284      pciS = pciSa[x];
     1285      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1286        pciD = pciDa[x];
     1287        if (CompSelectClearSelects(pciS,
     1288                                   pciD,
     1289                                   pciS->flags & CNRITEM_NEWER,
     1290                                   pciD->flags & CNRITEM_NEWER)) {
     1291          fUpdateHideButton = TRUE;
    13551292        }
    13561293      }
     
    13611298  case IDM_DESELECTOLDER:
    13621299    for (x = 0; x < numS; x++) {
    1363       if (~pciSa[x]->rc.flRecordAttr & CRA_FILTERED) {
    1364         if (pciSa[x]->flags & CNRITEM_OLDER) {
    1365           if (pciSa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1366             WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciSa[x]),
    1367                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1368             fUpdateHideButton = TRUE;
    1369           }
    1370         }
    1371         else if (pciDa[x]->flags & CNRITEM_OLDER) {
    1372           if (pciDa[x]->rc.flRecordAttr & CRA_SELECTED) {
    1373             WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciDa[x]),
    1374                        MPFROM2SHORT(FALSE, CRA_SELECTED));
    1375             fUpdateHideButton = TRUE;
    1376           }
     1300      pciS = pciSa[x];
     1301      if (~pciS->rc.flRecordAttr & CRA_FILTERED) {
     1302        pciD = pciDa[x];
     1303        if (CompSelectClearSelects(pciS,
     1304                                   pciD,
     1305                                   pciS->flags & CNRITEM_OLDER,
     1306                                   pciD->flags & CNRITEM_OLDER)) {
     1307          fUpdateHideButton = TRUE;
    13771308        }
    13781309      }
     
    13831314  default:
    13841315    break;
    1385   } // switch
    1386 
    1387   if (reset) {
    1388     while (numS) {
    1389       WinSendMsg(hwndCnrS, CM_INVALIDATERECORD,
    1390                  MPFROMP(pciSa), MPFROM2SHORT((min(numS, 65535)), 0));
    1391       WinSendMsg(hwndCnrD, CM_INVALIDATERECORD,
    1392                  MPFROMP(pciDa), MPFROM2SHORT((min(numD, 65535)), 0));
    1393       numS -= min(numS, 65535);
    1394       SleepIfNeeded(&itdSleep, 0);      // 12 Jan 08 SHL
    1395     } // while
    1396   }
     1316  } // switch action
    13971317
    13981318  free(pciSa);
     
    14301350    return;
    14311351  }
    1432 
    1433   // DbgMsg(pszSrcFile, __LINE__, "FillDirList start %s", str);
    14341352
    14351353  maskstr = xmalloc(CCHMAXPATH + 100, pszSrcFile, __LINE__);
     
    15221440  xfree(maskstr, pszSrcFile, __LINE__);
    15231441  xfree(pffbArray, pszSrcFile, __LINE__);
    1524 
    1525   // DbgMsg(pszSrcFile, __LINE__, "FillDirList finish %s", str);
    15261442}
     1443
     1444#define GetHwndLeft(h)  (WinWindowFromID(h,COMP_LEFTDIR))
     1445#define GetHwndRight(h) (WinWindowFromID(h,COMP_RIGHTDIR))
    15271446
    15281447/**
     
    15381457}
    15391458
    1540 //=== FillCnrsThread() Fill left and right containers ===
     1459/**
     1460 * Fill left and right containers
     1461 */
    15411462
    15421463static VOID FillCnrsThread(VOID *args)
     
    15481469  ITIMER_DESC itdSleep = { 0 };
    15491470
    1550   HWND hwndLeft, hwndRight;
    15511471  CHAR szBuf[CCHMAXPATH];
    15521472  CNRINFO cnri;
     
    15651485    return;                             // 10 Dec 08 SHL was _endthread
    15661486  }
    1567 
    1568   // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread enter");
    15691487
    15701488  DosError(FERR_DISABLEHARDERR);
     
    16021520      RECORDINSERT ri;
    16031521      CHAR *pch;
     1522      HWND hwndLeft;
     1523      HWND hwndRight;
    16041524
    16051525      WinCancelShutdown(hmq, TRUE);
    16061526      IncrThreadUsage();
    16071527
    1608       hwndLeft = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
    1609       hwndRight = WinWindowFromID(cmp->hwnd, COMP_RIGHTDIR);
     1528      hwndLeft = GetHwndLeft(cmp->hwnd);
     1529      hwndRight = GetHwndRight(cmp->hwnd);
    16101530      lenl = strlen(cmp->leftdir);
    16111531      if (cmp->leftdir[strlen(cmp->leftdir) - 1] != '\\')
     
    16311551      if (filesl)
    16321552        qsort(filesl, cmp->cmp->totalleft, sizeof(CHAR *), CompNames);
    1633 
    1634       // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread sorted filesl");
    16351553
    16361554      // Build list of all files in right directory
     
    17801698        qsort(filesr, cmp->cmp->totalright, sizeof(CHAR *), CompNames);
    17811699
    1782       // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread sorted filesr");
    1783 
    17841700      // We now have two lists of files, both sorted.
    17851701      // Count total number of container entries required on each side
     
    17881704      while ((filesl && filesl[l]) || (filesr && filesr[r])) {
    17891705
     1706        if (cmp->stop)
     1707          break;                        // Cancel requested
     1708
    17901709        if (filesl && filesl[l]) {
    17911710          if (filesr && filesr[r])
     
    18061725      } // while
    18071726
    1808       // Say building list - fixme to post?
    1809       WinSendMsg(cmp->hwnd, UM_CONTAINERHWND, MPVOID, MPVOID);
     1727      if (cmp->stop) {
     1728        recsNeeded = 0;
     1729      }
    18101730
    18111731      // Now insert records into the containers
     1732
    18121733      if (recsNeeded) {
     1734
     1735        // Use send to get message on screen quickly
     1736        WinSendMsg(cmp->hwnd, UM_CONTAINERHWND, MPVOID, MPVOID);
     1737
    18131738        pcilFirst = WinSendMsg(hwndLeft,
    18141739                               CM_ALLOCRECORD,
     
    18201745        }
    18211746      }
     1747
    18221748      if (recsNeeded) {
    18231749        pcirFirst = WinSendMsg(hwndRight, CM_ALLOCRECORD,
     
    18331759      if (recsNeeded) {
    18341760
    1835         // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread filling");
    1836 
    18371761        l = 0;
    18381762        r = 0;
     
    18481772        while ((filesl && filesl[l]) || (filesr && filesr[r])) {
    18491773
    1850           // 12 Jan 08 SHL fixme to have message in string table
     1774          if (cmp->stop)
     1775            break;
     1776
    18511777          if (!pcil) {
    1852             Runtime_Error(pszSrcFile, __LINE__, "Insufficient memory or %u items (%u)",
     1778            Runtime_Error(pszSrcFile, __LINE__, GetPString(IDS_INSUFFICIENTMEMORY),
    18531779                          recsNeeded, recsGotten);
    18541780            break;
    18551781          }
    18561782
    1857           // 12 Jan 08 SHL fixme to have message in string table
    18581783          if (!pcir) {
    1859             Runtime_Error(pszSrcFile, __LINE__, "Insufficient memory or %u items (%u)",
     1784            Runtime_Error(pszSrcFile, __LINE__, GetPString(IDS_INSUFFICIENTMEMORY),
    18601785                          recsNeeded, recsGotten);
    18611786            break;
     
    19791904            ret = TestCDates(&pcir->date, &pcir->time,
    19801905                             &pcil->date, &pcil->time);
    1981             if (ret == 1)
    1982               /* 13 Jan 08 SHL fixme to be gone
    1983                 ((pcil->date.year > pcir->date.year) ? TRUE :
    1984                 (pcil->date.year < pcir->date.year) ? FALSE :
    1985                 (pcil->date.month > pcir->date.month) ? TRUE :
    1986                 (pcil->date.month < pcir->date.month) ? FALSE :
    1987                 (pcil->date.day > pcir->date.day) ? TRUE :
    1988                 (pcil->date.day < pcir->date.day) ? FALSE :
    1989                 (pcil->time.hours > pcir->time.hours) ? TRUE :
    1990                 (pcil->time.hours < pcir->time.hours) ? FALSE :
    1991                 (pcil->time.minutes > pcir->time.minutes) ? TRUE :
    1992                 (pcil->time.minutes < pcir->time.minutes) ? FALSE :
    1993                 (pcil->time.seconds > pcir->time.seconds) ? TRUE :
    1994                 (pcil->time.seconds < pcir->time.seconds) ? FALSE : FALSE)
    1995                */
    1996             {
     1906            if (ret == 1) {
    19971907              pcil->flags |= CNRITEM_NEWER;
    19981908              pcir->flags |= CNRITEM_OLDER;
     
    20041914              pch += 5;
    20051915            }
    2006             else if (ret == -1)
    2007               /* 13 Jan 08 SHL fixme to be gone
    2008                 ((pcil->date.year < pcir->date.year) ? TRUE :
    2009                 (pcil->date.year > pcir->date.year) ? FALSE :
    2010                 (pcil->date.month < pcir->date.month) ? TRUE :
    2011                 (pcil->date.month > pcir->date.month) ? FALSE :
    2012                 (pcil->date.day < pcir->date.day) ? TRUE :
    2013                 (pcil->date.day > pcir->date.day) ? FALSE :
    2014                 (pcil->time.hours < pcir->time.hours) ? TRUE :
    2015                 (pcil->time.hours > pcir->time.hours) ? FALSE :
    2016                 (pcil->time.minutes < pcir->time.minutes) ? TRUE :
    2017                 (pcil->time.minutes > pcir->time.minutes) ? FALSE :
    2018                 (pcil->time.seconds < pcir->time.seconds) ? TRUE :
    2019                 (pcil->time.seconds > pcir->time.seconds) ? FALSE :
    2020                 FALSE)
    2021               */
    2022             {
     1916            else if (ret == -1) {
    20231917              pcil->flags |= CNRITEM_OLDER;
    20241918              pcir->flags |= CNRITEM_NEWER;
     
    21512045        }
    21522046
    2153         // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread filled");
    2154 
    21552047      } // if recsNeeded
    21562048
    21572049      Deselect(hwndLeft);
    21582050      Deselect(hwndRight);
    2159 
    2160       // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread deselected");
    21612051
    21622052      // Request window update
     
    21642054        WinSendMsg(cmp->hwnd, UM_CONTAINER_FILLED, MPVOID, MPVOID);
    21652055      notified = TRUE;
    2166 
    2167       // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread FILLED posted");
    21682056
    21692057      if (filesl)
     
    21862074#  endif
    21872075
    2188   // DbgMsg(pszSrcFile, __LINE__, "FillCnrsThread exit");
    21892076}
    21902077
    2191 // fixme to be gone - use variable?
    2192 #define hwndLeft        (WinWindowFromID(hwnd,COMP_LEFTDIR))
    2193 #define hwndRight       (WinWindowFromID(hwnd,COMP_RIGHTDIR))
    2194 
    2195 //=== CompareDlgProc() Compare directories dialog procedure ===
     2078/**
     2079 * Find matching item in other container
     2080 * @return PCNRITEM or NULL
     2081 */
     2082
     2083static PCNRITEM FindMatchingItem(PCNRITEM pciFindS, HWND hwndCnrS, HWND hwndCnrD);
     2084
     2085static PCNRITEM FindMatchingItem(PCNRITEM pciFindS, HWND hwndCnrS, HWND hwndCnrD)
     2086{
     2087
     2088  PCNRITEM pciS;
     2089  PCNRITEM pciD;
     2090
     2091  pciS = WinSendMsg(hwndCnrS, CM_QUERYRECORD, MPVOID,
     2092                   MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
     2093  pciD = WinSendMsg(hwndCnrD, CM_QUERYRECORD, MPVOID,
     2094                    MPFROM2SHORT(CMA_FIRST, CMA_ITEMORDER));
     2095  while (pciS && (INT)pciS != -1 && pciD && (INT)pciD != -1) {
     2096
     2097    if (pciS == pciFindS)
     2098      break;
     2099
     2100    pciS = WinSendMsg(hwndCnrS, CM_QUERYRECORD, MPFROMP(pciS),
     2101                      MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
     2102    pciD = WinSendMsg(hwndCnrD, CM_QUERYRECORD, MPFROMP(pciD),
     2103                       MPFROM2SHORT(CMA_NEXT, CMA_ITEMORDER));
     2104  } // while
     2105
     2106  if (pciS != pciFindS)
     2107    pciD = NULL;
     2108
     2109  return pciD;
     2110}
     2111
     2112/**
     2113 * Set button/window enables
     2114 */
     2115
     2116static VOID SetButtonEnables(COMPARE* cmp, BOOL fEnable);
     2117
     2118static VOID SetButtonEnables(COMPARE* cmp, BOOL fEnable)
     2119{
     2120  HWND hwnd = cmp->hwnd;
     2121  HWND hwndLeft = GetHwndLeft(hwnd);
     2122  HWND hwndRight = GetHwndRight(hwnd);
     2123
     2124  if (!fEnable) {
     2125    /* Disable before */
     2126    WinEnableWindowUpdate(hwndLeft, fEnable);
     2127    WinEnableWindowUpdate(hwndRight, fEnable);
     2128  }
     2129  WinEnableWindow(hwndLeft, fEnable);
     2130  WinEnableWindow(hwndRight, fEnable);
     2131  if (fEnable) {
     2132    /* Enable after */
     2133    WinEnableWindowUpdate(hwndLeft, fEnable);
     2134    WinEnableWindowUpdate(hwndRight, fEnable);
     2135  }
     2136
     2137  WinEnableWindow(WinWindowFromID(hwnd, DID_OK), fEnable);
     2138  // WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), fEnable);
     2139  WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), fEnable);
     2140  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), fEnable);
     2141  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), fEnable);
     2142  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), fEnable);
     2143  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), fEnable);
     2144  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), fEnable);
     2145  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), fEnable);
     2146  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), fEnable);
     2147  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), fEnable);
     2148  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), fEnable);
     2149  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), fEnable);
     2150  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), fEnable);
     2151  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), fEnable);
     2152  WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), fEnable);
     2153  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT), fEnable);
     2154  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), fEnable);
     2155  WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), fEnable);
     2156  WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), fEnable);
     2157  WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), fEnable);
     2158  WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), fEnable);
     2159  WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), fEnable);
     2160  if (!fEnable || !*cmp->rightlist ) {
     2161    WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), fEnable);
     2162    WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), fEnable);
     2163    WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), fEnable);
     2164    WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), fEnable);
     2165    WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), fEnable);
     2166  }
     2167  WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), fEnable);
     2168  WinEnableWindow(WinWindowFromID(hwnd, COMP_HIDENOTSELECTED), fEnable);
     2169}
     2170
     2171/**
     2172 * Compare directories dialog procedure
     2173 */
    21962174
    21972175MRESULT EXPENTRY CompareDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
     
    21992177  COMPARE *cmp;
    22002178  BOOL temp;
     2179  CHAR szPathName[CCHMAXPATH];
    22012180  CHAR s[81];
    22022181
     
    22302209                        swp.fl);
    22312210      }
    2232       SetCnrCols(hwndLeft, TRUE);
    2233       SetCnrCols(hwndRight, TRUE);
     2211      SetCnrCols(GetHwndLeft(hwnd), TRUE);
     2212      SetCnrCols(GetHwndRight(hwnd), TRUE);
    22342213      WinSendMsg(hwnd, UM_SETUP, MPVOID, MPVOID);
    22352214      WinSendMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
     
    23202299        PaintRecessedWindow(WinWindowFromID(hwnd, COMP_SELRIGHT),
    23212300                            (HPS)0, FALSE, FALSE);
    2322         PaintRecessedWindow(hwndLeft, (HPS)0,
    2323                             (hwndActive == hwndLeft), TRUE);
    2324         PaintRecessedWindow(hwndRight, (HPS)0,
    2325                             (hwndActive == hwndRight), TRUE);
     2301        PaintRecessedWindow(GetHwndLeft(hwnd), (HPS)0,
     2302                            (hwndActive == GetHwndLeft(hwnd)), TRUE);
     2303        PaintRecessedWindow(GetHwndRight(hwnd), (HPS)0,
     2304                            (hwndActive == GetHwndRight(hwnd)), TRUE);
    23262305      }
    23272306    }
     
    23672346      WinSendDlgItemMsg(hwnd, COMP_RIGHTDIR, CM_SETCNRINFO, MPFROMP(&cnri),
    23682347                        MPFROMLONG(CMA_FLWINDOWATTR | CMA_XVERTSPLITBAR));
    2369       AdjustCnrColRO(hwndLeft, GetPString(IDS_FILENAMECOLTEXT), TRUE, FALSE);
    2370       AdjustCnrColRO(hwndLeft, GetPString(IDS_LONGNAMECOLTEXT), TRUE, FALSE);
    2371       AdjustCnrColRO(hwndRight, GetPString(IDS_FILENAMECOLTEXT), TRUE, FALSE);
    2372       AdjustCnrColRO(hwndRight, GetPString(IDS_LONGNAMECOLTEXT), TRUE, FALSE);
    2373       AdjustCnrColsForPref(hwndLeft, cmp->leftdir, &cmp->dcd.ds, TRUE);
     2348      AdjustCnrColRO(GetHwndLeft(hwnd), GetPString(IDS_FILENAMECOLTEXT), TRUE, FALSE);
     2349      AdjustCnrColRO(GetHwndLeft(hwnd), GetPString(IDS_LONGNAMECOLTEXT), TRUE, FALSE);
     2350      AdjustCnrColRO(GetHwndRight(hwnd), GetPString(IDS_FILENAMECOLTEXT), TRUE, FALSE);
     2351      AdjustCnrColRO(GetHwndRight(hwnd), GetPString(IDS_LONGNAMECOLTEXT), TRUE, FALSE);
     2352      AdjustCnrColsForPref(GetHwndLeft(hwnd), cmp->leftdir, &cmp->dcd.ds, TRUE);
    23742353      tempsubj = cmp->dcd.ds.detailssubject;
    23752354      cmp->dcd.ds.detailssubject = FALSE;
    2376       AdjustCnrColsForPref(hwndRight, cmp->rightdir, &cmp->dcd.ds, TRUE);
     2355      AdjustCnrColsForPref(GetHwndRight(hwnd), cmp->rightdir, &cmp->dcd.ds, TRUE);
    23772356      if (*cmp->rightlist) {
    2378         AdjustCnrColVis(hwndRight, GetPString(IDS_LADATECOLTEXT), FALSE,
     2357        AdjustCnrColVis(GetHwndRight(hwnd), GetPString(IDS_LADATECOLTEXT), FALSE,
    23792358                        FALSE);
    2380         AdjustCnrColVis(hwndRight, GetPString(IDS_LATIMECOLTEXT), FALSE,
     2359        AdjustCnrColVis(GetHwndRight(hwnd), GetPString(IDS_LATIMECOLTEXT), FALSE,
    23812360                        FALSE);
    2382         AdjustCnrColVis(hwndRight, GetPString(IDS_CRDATECOLTEXT), FALSE,
     2361        AdjustCnrColVis(GetHwndRight(hwnd), GetPString(IDS_CRDATECOLTEXT), FALSE,
    23832362                        FALSE);
    2384         AdjustCnrColVis(hwndRight, GetPString(IDS_CRTIMECOLTEXT), FALSE,
     2363        AdjustCnrColVis(GetHwndRight(hwnd), GetPString(IDS_CRTIMECOLTEXT), FALSE,
    23852364                        FALSE);
    23862365      }
     
    24532432      WinDismissDlg(hwnd, 0);
    24542433    }
     2434    else if (cmp->stop) {
     2435      // Delayed cancel
     2436      WinDismissDlg(hwnd, 1);
     2437    }
    24552438    else {
    24562439      cmp->filling = FALSE;
    2457       WinEnableWindow(hwndLeft, TRUE);
    2458       WinEnableWindow(hwndRight, TRUE);
    2459       WinEnableWindowUpdate(hwndLeft, TRUE);
    2460       WinEnableWindowUpdate(hwndRight, TRUE);
    2461       WinPostMsg(hwnd, WM_TIMER, MPFROMLONG(ID_COMP_TIMER), 0); // Force update
    2462       // 12 Jan 08 SHL fixme to have SetButtonEnables(COMPARE* pcmp, BOOL fEnable)
    2463       // to replace duplicated code here and elsewhere
    2464       WinEnableWindow(WinWindowFromID(hwnd, DID_OK), TRUE);
    2465       WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), TRUE);
    2466       WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), TRUE);
    2467       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), TRUE);
    2468       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), TRUE);
    2469       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), TRUE);
    2470       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), TRUE);
    2471       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), TRUE);
    2472       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), TRUE);
    2473       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), TRUE);
    2474       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), TRUE);
    2475       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), TRUE);
    2476       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), TRUE);
    2477       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), TRUE);
    2478       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), TRUE);
    2479       WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), TRUE);
    2480       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT), TRUE);
    2481       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), TRUE);
    2482       WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), TRUE);
    2483       WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), TRUE);
    2484       WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), TRUE);
    2485       WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), TRUE);
    2486       WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), TRUE);
    2487       if (!*cmp->rightlist) {
    2488         WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), TRUE);
    2489         WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), TRUE);
    2490         WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), TRUE);
    2491         WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), TRUE);
    2492         WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), TRUE);
    2493       }
    2494       WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), TRUE);
    2495       WinEnableWindow(WinWindowFromID(hwnd, COMP_HIDENOTSELECTED), TRUE);
     2440      SetButtonEnables(cmp, TRUE);
     2441      WinPostMsg(hwnd, WM_TIMER, MPFROMLONG(ID_COMP_TIMER), 0); // Force counts to update
    24962442      if (*cmp->dcd.mask.szMask) {
    2497         sprintf(s,
    2498                 GetPString(IDS_COMPREADYFILTEREDTEXT),
    2499                 cmp->dcd.mask.szMask);
     2443        sprintf(s, GetPString(IDS_COMPREADYFILTEREDTEXT), cmp->dcd.mask.szMask);
    25002444        WinSetDlgItemText(hwnd, COMP_NOTE, s);
    25012445      }
     
    25202464    if (cmp) {
    25212465      if ((HWND)mp2 == cmp->dcd.hwndLastMenu) {
    2522         MarkAll(hwndLeft, TRUE, FALSE, TRUE);
    2523         MarkAll(hwndRight, TRUE, FALSE, TRUE);
     2466        MarkAll(GetHwndLeft(hwnd), TRUE, FALSE, TRUE);
     2467        MarkAll(GetHwndRight(hwnd), TRUE, FALSE, TRUE);
    25242468        WinDestroyWindow(cmp->dcd.hwndLastMenu);
    25252469        cmp->dcd.hwndLastMenu = (HWND)0;
     
    25952539        if (cmp) {
    25962540          PCNRITEM pci = (PCNRITEM)mp2;
    2597           USHORT id = COMP_CNRMENU;
     2541          USHORT id = COMP_CNRMENU;             // Assume container menu
    25982542
    25992543          if (cmp->dcd.hwndLastMenu)
     
    26042548            if (!pci || !*pci->pszFileName || *cmp->rightlist)
    26052549              break;
    2606             id = COMP_MENU;
     2550            id = COMP_MENU;             // Want container item menu
    26072551            WinSendMsg(cmp->hwndCalling, CM_SETRECORDEMPHASIS,
    26082552                       MPFROMP(pci), MPFROM2SHORT(TRUE, CRA_CURSORED));
     
    26102554          cmp->dcd.hwndLastMenu = WinLoadMenu(HWND_DESKTOP, FM3ModHandle, id);
    26112555          if (cmp->dcd.hwndLastMenu) {
    2612             if (id == COMP_CNRMENU) {
     2556            switch (id) {
     2557            case COMP_CNRMENU:
    26132558              if (SHORT1FROMMP(mp1) == COMP_RIGHTDIR)
    26142559                WinSendMsg(cmp->dcd.hwndLastMenu, MM_DELETEITEM,
     
    26212566                WinSendMsg(cmp->dcd.hwndLastMenu, MM_DELETEITEM,
    26222567                           MPFROM2SHORT(IDM_SAVELISTFILE, 0), MPVOID);
    2623             }
     2568              break;
     2569            case COMP_MENU:
     2570              // Can't compare what's not there
     2571              if (~pci->flags & CNRITEM_EXISTS) {
     2572                WinSendMsg(cmp->dcd.hwndLastMenu, MM_DELETEITEM,
     2573                           MPFROM2SHORT(IDM_COMPARE, 0), MPVOID);
     2574              }
     2575              break;
     2576            } // switch
    26242577            PopupMenu(hwnd, hwnd, cmp->dcd.hwndLastMenu);
    26252578          }
     
    26532606                // Slot empty
    26542607                // 17 Jan 08 SHL fixme to know how can get here
     2608                Runtime_Error(pszSrcFile, __LINE__, NULL);
    26552609                // 12 Jan 08 SHL fixme to know if select counts need update?
    26562610                if (pci->rc.flRecordAttr & CRA_SELECTED)
     
    27572711        }
    27582712        else {
    2759           WinEnableWindowUpdate(hwndLeft, FALSE);
    2760           WinEnableWindowUpdate(hwndRight, FALSE);
    2761           cmp->selleft = cmp->selright = 0;
    27622713          WinSetDlgItemText(hwnd, COMP_NOTE,
    27632714                            GetPString(IDS_COMPHOLDREADDISKTEXT));
    2764           WinEnableWindow(hwndRight, FALSE);
    2765           WinEnableWindow(hwndLeft, FALSE);
    2766           WinEnableWindow(WinWindowFromID(hwnd, DID_OK), FALSE);
    2767           WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), FALSE);
    2768           WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), FALSE);
    2769           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), FALSE);
    2770           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), FALSE);
    2771           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), FALSE);
    2772           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), FALSE);
    2773           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), FALSE);
    2774           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), FALSE);
    2775           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), FALSE);
    2776           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), FALSE);
    2777           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), FALSE);
    2778           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), FALSE);
    2779           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), FALSE);
    2780           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), FALSE);
    2781           WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), FALSE);
    2782           WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), FALSE);
    2783           WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), FALSE);
    2784           WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), FALSE);
    2785           WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), FALSE);
    2786           WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), FALSE);
    2787           WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), FALSE);
    2788           WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), FALSE);
    2789           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT), FALSE);
    2790           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), FALSE);
    2791           WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), FALSE);
    2792           WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), FALSE);
    2793           WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), FALSE);
    2794           WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), FALSE);
    2795           WinEnableWindow(WinWindowFromID(hwnd, COMP_HIDENOTSELECTED), FALSE);
     2715          SetButtonEnables(cmp, FALSE);
     2716          cmp->selleft = 0;
     2717          cmp->selright = 0;
    27962718        }
    27972719      }
     
    28112733      // cmp->dcd.suspendview = 1;      // 12 Jan 08 SHL appears not to be used here
    28122734      priority_idle();                  // Don't hog resources
    2813       WinSendMsg(hwndLeft, CM_FILTER, MPFROMP(Filter),
     2735      WinSendMsg(GetHwndLeft(hwnd), CM_FILTER, MPFROMP(Filter),
    28142736                 MPFROMP(&cmp->dcd.mask));
    2815       WinSendMsg(hwndRight, CM_FILTER, MPFROMP(Filter),
     2737      WinSendMsg(GetHwndRight(hwnd), CM_FILTER, MPFROMP(Filter),
    28162738                 MPFROMP(&cmp->dcd.mask));
    28172739      priority_normal();
     
    28322754    if (cmp) {
    28332755      ULONG wasHidden = WinQueryButtonCheckstate(hwnd,
    2834                                                   COMP_HIDENOTSELECTED);
     2756                                                 COMP_HIDENOTSELECTED);
     2757      ULONG nowHidden = wasHidden != 1 && (cmp->selleft || cmp->selright);
    28352758
    28362759      // cmp->dcd.suspendview = 1;      // 12 Jan 08 SHL appears not to be used here
    2837       if (wasHidden != 1) {
    2838         // Hide if not selected on both sides
     2760      // 26 Sep 09 SHL Unhide if nothing selected
     2761      if (nowHidden) {
     2762        // Hide items not selected on both sides
    28392763        BOOL needRefresh = FALSE;
    28402764        HWND hwndl = WinWindowFromID(cmp->hwnd, COMP_LEFTDIR);
     
    28482772          if (~pcil->rc.flRecordAttr & CRA_SELECTED &&
    28492773              ~pcir->rc.flRecordAttr & CRA_SELECTED) {
    2850             // 17 Jan 08 SHL fixme to optimize refresh
    2851             pcil->rc.flRecordAttr |= CRA_FILTERED;
    2852             pcir->rc.flRecordAttr |= CRA_FILTERED;
    2853             needRefresh = TRUE;
     2774            if (~pcil->rc.flRecordAttr & CRA_FILTERED) {
     2775              needRefresh = TRUE;
     2776              pcil->rc.flRecordAttr |= CRA_FILTERED;
     2777            }
     2778            if (~pcir->rc.flRecordAttr & CRA_FILTERED) {
     2779              pcir->rc.flRecordAttr |= CRA_FILTERED;
     2780              needRefresh = TRUE;
     2781            }
    28542782          }
    28552783          pcil = WinSendMsg(hwndl, CM_QUERYRECORD, MPFROMP(pcil),
     
    28672795      else {
    28682796        // Unhide
    2869         WinSendMsg(hwndLeft, CM_FILTER, MPFROMP(Filter),
     2797        WinSendMsg(GetHwndLeft(hwnd), CM_FILTER, MPFROMP(Filter),
    28702798                   MPFROMP(&cmp->dcd.mask));
    2871         WinSendMsg(hwndRight, CM_FILTER, MPFROMP(Filter),
     2799        WinSendMsg(GetHwndRight(hwnd), CM_FILTER, MPFROMP(Filter),
    28722800                   MPFROMP(&cmp->dcd.mask));
    28732801      }
     
    28812809      else
    28822810        WinSetDlgItemText(hwnd, COMP_NOTE, GetPString(IDS_COMPREADYTEXT));
    2883       WinCheckButton(hwnd, COMP_HIDENOTSELECTED, wasHidden != 1 ? 1 : 0);
     2811      WinCheckButton(hwnd, COMP_HIDENOTSELECTED, nowHidden);
    28842812    }
    28852813    return 0;
    28862814
    28872815  case WM_COMMAND:
    2888     // 29 Apr 09 SHL  fixme to support more context menu items - IDM_EDIT, IDM_DELETE etc.
     2816    // 29 Apr 09 SHL fixme to support more context menu items - IDM_VIEW, IDM_EDIT etc.
    28892817    switch (SHORT1FROMMP(mp1)) {
    28902818    case IDM_COMPARE:
     
    28922820      if (cmp) {
    28932821        PCNRITEM pci;
    2894         CHAR ofile[CCHMAXPATH];
    2895 
    28962822        pci = (PCNRITEM)WinSendMsg(cmp->hwndCalling,
    28972823                                   CM_QUERYRECORDEMPHASIS,
    28982824                                   MPFROMLONG(CMA_FIRST),
    28992825                                   MPFROMSHORT(CRA_CURSORED));
    2900         // 01 Aug 07 SHL
    29012826        if (pci && *pci->pszFileName) {
    2902           if (cmp->hwndCalling == hwndLeft)
    2903             strcpy(ofile, cmp->rightdir);
     2827          if (cmp->hwndCalling == GetHwndLeft(hwnd))
     2828            strcpy(szPathName, cmp->rightdir);
    29042829          else
    2905             strcpy(ofile, cmp->leftdir);
    2906           AddBackslashToPath(ofile);
    2907           //if (ofile[strlen(ofile) - 1] != '\\')
    2908           //  strcat(ofile, "\\");
    2909           strcat(ofile, pci->pszDisplayName);
     2830            strcpy(szPathName, cmp->leftdir);
     2831          AddBackslashToPath(szPathName);
     2832          strcat(szPathName, pci->pszDisplayName);
    29102833          if (*compare) {
    29112834            CHAR *fakelist[3];
    29122835            fakelist[0] = pci->pszFileName;
    2913             fakelist[1] = ofile;
     2836            fakelist[1] = szPathName;
    29142837            fakelist[2] = NULL;
    29152838            ExecOnList(hwnd, compare,
     
    29232846            fc.hwndParent = hwnd;
    29242847            strcpy(fc.file1, pci->pszFileName);
    2925             strcpy(fc.file2, ofile);
     2848            strcpy(fc.file2, szPathName);
    29262849            WinDlgBox(HWND_DESKTOP, hwnd,
    29272850                      CFileDlgProc, FM3ModHandle, FCMP_FRAME, (PVOID)&fc);
     
    29302853      }
    29312854      break;
     2855
     2856    case IDM_DELETE:
     2857      cmp = INSTDATA(hwnd);
     2858      if (!cmp)
     2859        Runtime_Error(pszSrcFile, __LINE__, NULL);
     2860      else {
     2861        PCNRITEM pciS;
     2862        PCNRITEM pciD;
     2863        HWND hwndCnrS;
     2864        HWND hwndCnrD;
     2865        pciS = (PCNRITEM)WinSendMsg(cmp->hwndCalling,
     2866                                   CM_QUERYRECORDEMPHASIS,
     2867                                   MPFROMLONG(CMA_FIRST),
     2868                                   MPFROMSHORT(CRA_CURSORED));
     2869        if (!pciS)
     2870          Runtime_Error(pszSrcFile, __LINE__, NULL);
     2871        else {
     2872          // Find matching record
     2873          if (cmp->hwndCalling == GetHwndLeft(hwnd)) {
     2874            hwndCnrS = GetHwndLeft(hwnd);
     2875            hwndCnrD = GetHwndRight(hwnd);
     2876          }
     2877          else {
     2878            hwndCnrS = GetHwndRight(hwnd);
     2879            hwndCnrD = GetHwndLeft(hwnd);
     2880          }
     2881
     2882          pciD = FindMatchingItem(pciS, hwndCnrS, hwndCnrD);
     2883
     2884          if (!pciD)
     2885            Runtime_Error(pszSrcFile, __LINE__, NULL);
     2886          else if (!pciS->pszFileName)
     2887            Runtime_Error(pszSrcFile, __LINE__, NULL);
     2888          else {
     2889            if (!unlinkf(pciS->pszFileName)) {
     2890              WinSendMsg(hwndCnrS, CM_SETRECORDEMPHASIS, MPFROMP(pciS),
     2891                         MPFROM2SHORT(FALSE, CRA_SELECTED));
     2892
     2893              if (!*pciD->pszFileName) {
     2894                // Other side is blank - remove from both sides
     2895                RemoveCnrItems(hwndCnrS, pciS, 1, CMA_FREE | CMA_INVALIDATE);
     2896                if (pciD->rc.flRecordAttr & CRA_SELECTED)
     2897                  WinSendMsg(hwndCnrD, CM_SETRECORDEMPHASIS, MPFROMP(pciD),
     2898                             MPFROM2SHORT(FALSE, CRA_SELECTED));
     2899                RemoveCnrItems(hwndCnrD, pciD, 1, CMA_FREE | CMA_INVALIDATE);
     2900              }
     2901              else {
     2902                // Other side is not blank - just blank this side
     2903                FreeCnrItemData(pciS);
     2904                pciS->pszFileName = NullStr;
     2905                pciS->pszDisplayName = pciS->pszFileName;
     2906                pciS->rc.pszIcon = pciS->pszFileName;
     2907                pciS->flags = 0;        // Just on one side
     2908                WinSendMsg(hwndCnrS, CM_INVALIDATERECORD, MPFROMP(&pciS),
     2909                           MPFROM2SHORT(1, CMA_ERASE | CMA_TEXTCHANGED));
     2910                pciD->flags = 0;        // Just on one side
     2911                if (pciD->pszSubject != NullStr) {
     2912                  xfree(pciD->pszSubject, pszSrcFile, __LINE__);
     2913                  pciD->pszSubject = NullStr;
     2914                }
     2915              }
     2916              if (hwndCnrS == GetHwndLeft(hwnd))
     2917                cmp->totalleft--;
     2918              else
     2919                cmp->totalright--;
     2920              // Force displayed counts to update
     2921              WinPostMsg(hwnd, WM_TIMER, MPFROMLONG(ID_COMP_TIMER), 0);
     2922            }
     2923          }
     2924        }
     2925      }
     2926      break; // IDM_DELETE
    29322927
    29332928    case COMP_FILTER:
     
    29882983
    29892984        dcd1 = cmp->dcd;
    2990         AdjustDetailsSwitches(hwndLeft,
     2985        AdjustDetailsSwitches(GetHwndLeft(hwnd),
    29912986                              (HWND)0, SHORT1FROMMP(mp1),
    29922987                              cmp->leftdir, PCSZ_DIRCMP, &cmp->dcd.ds, TRUE);
     
    29942989        cmp->dcd = dcd1;
    29952990        cmp->dcd.ds.detailssubject = FALSE;
    2996         AdjustDetailsSwitches(hwndRight,
     2991        AdjustDetailsSwitches(GetHwndRight(hwnd),
    29972992                              cmp->dcd.hwndLastMenu, SHORT1FROMMP(mp1),
    29982993                              cmp->rightdir, PCSZ_DIRCMP, &cmp->dcd.ds, TRUE);
    2999         cmp->dcd.ds.detailssubject = tempsubj;
    3000         WriteDetailsSwitches(PCSZ_DIRCMP, &cmp->dcd.ds, TRUE);
     2994        cmp->dcd.ds.detailssubject = tempsubj;
     2995        WriteDetailsSwitches(PCSZ_DIRCMP, &cmp->dcd.ds, TRUE);
    30012996      }
    30022997      break;
     
    30293024          if (sf) {
    30303025            strcpy(sf->filename, fullname);
    3031             if (hwndLeft == cmp->hwndCalling)
     3026            if (GetHwndLeft(hwnd) == cmp->hwndCalling)
    30323027              strcpy(sf->dirname, cmp->leftdir);
    30333028            else
    30343029              strcpy(sf->dirname, cmp->rightdir);
    30353030            sf->recurse = cmp->includesubdirs;
    3036             if (xbeginthread(StartSnap,
     3031            if (xbeginthread(StartSnapThread,
    30373032                             65536,
    30383033                             sf,
     
    30973092          }
    30983093          else {
    3099             WinEnableWindowUpdate(hwndLeft, FALSE);
    3100             WinEnableWindowUpdate(hwndRight, FALSE);
     3094            WinEnableWindowUpdate(GetHwndLeft(hwnd), FALSE);
     3095            WinEnableWindowUpdate(GetHwndRight(hwnd), FALSE);
    31013096            switch (SHORT1FROMMP(mp1)) {
    31023097            case COMP_DELETELEFT:
     
    31183113              Runtime_Error(pszSrcFile, __LINE__, "mp1 %u unexpected", SHORT1FROMMP(mp1));
    31193114            }
    3120             WinEnableWindow(hwndRight, FALSE);
    3121             WinEnableWindow(hwndLeft, FALSE);
    3122             WinEnableWindow(WinWindowFromID(hwnd, DID_OK), FALSE);
    3123             WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), FALSE);
    3124             WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), FALSE);
    3125             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), FALSE);
    3126             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), FALSE);
    3127             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), FALSE);
    3128             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), FALSE);
    3129             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), FALSE);
    3130             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), FALSE);
    3131             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), FALSE);
    3132             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), FALSE);
    3133             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), FALSE);
    3134             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), FALSE);
    3135             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), FALSE);
    3136             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), FALSE);
    3137             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), FALSE);
    3138             WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), FALSE);
    3139             WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), FALSE);
    3140             WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), FALSE);
    3141             WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), FALSE);
    3142             WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), FALSE);
    3143             WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), FALSE);
    3144             WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), FALSE);
    3145             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT), FALSE);
    3146             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), FALSE);
    3147             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), FALSE);
    3148             WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), FALSE);
    3149             WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), FALSE);
    3150             WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), FALSE);
    3151             WinEnableWindow(WinWindowFromID(hwnd, COMP_HIDENOTSELECTED), FALSE);
     3115            SetButtonEnables(cmp, FALSE);
    31523116          }
    31533117        }
     
    31673131      break;
    31683132    case DID_CANCEL:
     3133      cmp = INSTDATA(hwnd);
     3134      if (!cmp)
     3135        Runtime_Error(pszSrcFile, __LINE__, NULL);
     3136      else {
     3137        cmp->stop = TRUE;                       // In case thread running
     3138        if (cmp->filling)
     3139          break;                                // UM_CONTAINER_FILLED will dismiss
     3140      }
    31693141      {
    31703142        SWP swp;
    31713143        ULONG size = sizeof(SWP);
    3172 
    31733144        WinQueryWindowPos(hwnd, &swp);
    31743145        PrfWriteProfileData(fmprof, FM3Str, "CompDir.Position", (PVOID) &swp,
     
    32133184          forthread->cmp = cmp;
    32143185          forthread->action = SHORT1FROMMP(mp1);
     3186          SetShiftState();
     3187          forthread->shiftstate = shiftstate;   // For and'ed actions
     3188
    32153189          if (xbeginthread(SelectCnrsThread,
    32163190                           65536,
     
    32223196          }
    32233197          else {
    3224             WinEnableWindowUpdate(hwndLeft, FALSE);
    3225             WinEnableWindowUpdate(hwndRight, FALSE);
     3198            WinEnableWindowUpdate(GetHwndLeft(hwnd), FALSE);
     3199            WinEnableWindowUpdate(GetHwndRight(hwnd), FALSE);
    32263200            switch (SHORT1FROMMP(mp1)) {
    32273201            case IDM_DESELECTALL:
     
    32443218              break;
    32453219            }
    3246             WinEnableWindow(hwndRight, FALSE);
    3247             WinEnableWindow(hwndLeft, FALSE);
    3248             WinEnableWindow(WinWindowFromID(hwnd, DID_OK), FALSE);
    3249             WinEnableWindow(WinWindowFromID(hwnd, DID_CANCEL), FALSE);
    3250             WinEnableWindow(WinWindowFromID(hwnd, COMP_COLLECT), FALSE);
    3251             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBOTH), FALSE);
    3252             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTONE), FALSE);
    3253             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTNEWER), FALSE);
    3254             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTOLDER), FALSE);
    3255             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTBIGGER), FALSE);
    3256             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSMALLER), FALSE);
    3257             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBOTH), FALSE);
    3258             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTONE), FALSE);
    3259             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTNEWER), FALSE);
    3260             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTOLDER), FALSE);
    3261             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTBIGGER), FALSE);
    3262             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTSMALLER), FALSE);
    3263             WinEnableWindow(WinWindowFromID(hwnd, IDM_DESELECTALL), FALSE);
    3264             WinEnableWindow(WinWindowFromID(hwnd, COMP_INCLUDESUBDIRS), FALSE);
    3265             WinEnableWindow(WinWindowFromID(hwnd, COMP_HIDENOTSELECTED), FALSE);
    3266             WinEnableWindow(WinWindowFromID(hwnd, COMP_SETDIRS), FALSE);
    3267             WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETELEFT), FALSE);
    3268             WinEnableWindow(WinWindowFromID(hwnd, COMP_DELETERIGHT), FALSE);
    3269             WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYLEFT), FALSE);
    3270             WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVELEFT), FALSE);
    3271             WinEnableWindow(WinWindowFromID(hwnd, COMP_COPYRIGHT), FALSE);
    3272             WinEnableWindow(WinWindowFromID(hwnd, COMP_MOVERIGHT), FALSE);
    3273             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAMECONTENT), FALSE);
    3274             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTIDENTICAL), FALSE);
    3275             WinEnableWindow(WinWindowFromID(hwnd, IDM_SELECTSAME), FALSE);
    3276             WinEnableWindow(WinWindowFromID(hwnd, IDM_INVERT), FALSE);
    3277             WinEnableWindow(WinWindowFromID(hwnd, COMP_FILTER), FALSE);
     3220            SetButtonEnables(cmp, FALSE);
    32783221          }
    32793222        }
     
    33263269        temp = fSelectedAlways;
    33273270        fSelectedAlways = TRUE;
    3328         listl = BuildList(hwndLeft);
     3271        listl = BuildList(GetHwndLeft(hwnd));
    33293272        if (!*cmp->rightlist)
    3330           listr = BuildList(hwndRight);
     3273          listr = BuildList(GetHwndRight(hwnd));
    33313274        fSelectedAlways = temp;
    33323275
     
    33553298      }
    33563299      break;
     3300    } // switch mp1
     3301    return 0;
     3302
     3303  case WM_CLOSE:
     3304    cmp = INSTDATA(hwnd);
     3305    if (!cmp)
     3306      Runtime_Error(pszSrcFile, __LINE__, NULL);
     3307    else {
     3308      cmp->stop = TRUE;                 // In case thread running
     3309      if (cmp->filling)
     3310        break;                          // UM_CONTAINER_FILLED will dismiss
    33573311    }
    3358     return 0;
    3359 
    3360   case WM_CLOSE:
    3361     // 18 Jan 08 SHL fixme to hold off if thread busy?
    33623312    WinDismissDlg(hwnd, 0);
    33633313    return 0;
     
    33773327      free(cmp);
    33783328    }
    3379     EmptyCnr(hwndLeft);
    3380     EmptyCnr(hwndRight);
     3329    EmptyCnr(GetHwndLeft(hwnd));
     3330    EmptyCnr(GetHwndRight(hwnd));
    33813331    DosPostEventSem(CompactSem);
    33823332    break;
     
    33853335}
    33863336
     3337#undef GetHwndLeft
     3338#undef GetHwndRight
     3339
    33873340#pragma alloc_text(COMPAREDIR,FillCnrsThread,FillDirList,CompNames,BldFullPathName)
    33883341#pragma alloc_text(COMPAREDIR1,CompareDlgProc)
    33893342#pragma alloc_text(COMPAREDIR2,SelectCnrsThread,ActionCnrThread)
    33903343#pragma alloc_text(COMPAREFILE,CFileDlgProc,CompareFilesThread)
    3391 #pragma alloc_text(SNAPSHOT,SnapShot,StartSnap)
    3392 #pragma alloc_text(COMPSELECT,CompSelect)
    3393 
     3344#pragma alloc_text(SNAPSHOT,SnapShot,StartSnapThread)
     3345#pragma alloc_text(COMPSELECT,CompSelect,CompSelectSetSelects,CompSelectClearSelects)
     3346
Note: See TracChangeset for help on using the changeset viewer.