[Try2] winhelp: add preliminary *.cnt file support (parser)
Kirill K. Smirnov
lich at math.spbu.ru
Sun Nov 19 07:01:35 CST 2006
ChangeLog:
Add preliminary *.cnt file support (parser)
-------------- next part --------------
diff --git a/programs/winhelp/hlpfile.c b/programs/winhelp/hlpfile.c
index e95dfdf..f61da8d 100644
--- a/programs/winhelp/hlpfile.c
+++ b/programs/winhelp/hlpfile.c
@@ -74,6 +74,8 @@ static struct
HLPFILE_LINK* link;
} attributes;
+static HLPFILE_CNT* HLPFILE_ReadCntFile(LPCSTR);
+static void HLPFILE_FreeCnt(HLPFILE_CNT*);
static BOOL HLPFILE_DoReadHlpFile(HLPFILE*, LPCSTR);
static BOOL HLPFILE_ReadFileToBuffer(HFILE);
static BOOL HLPFILE_FindSubFile(LPCSTR name, BYTE**, BYTE**);
@@ -256,6 +258,7 @@ HLPFILE *HLPFILE_ReadHlpFile(LPCSTR lpsz
hlpfile->lpszPath = (char*)hlpfile + sizeof(HLPFILE);
hlpfile->lpszTitle = NULL;
hlpfile->lpszCopyright = NULL;
+ hlpfile->lpszCntPath = NULL;
hlpfile->first_page = NULL;
hlpfile->first_macro = NULL;
hlpfile->wContextLen = 0;
@@ -263,6 +266,7 @@ HLPFILE *HLPFILE_ReadHlpFile(LPCSTR lpsz
hlpfile->wMapLen = 0;
hlpfile->Map = NULL;
hlpfile->contents_start = 0xFFFFFFFF;
+ hlpfile->cnt = NULL;
hlpfile->prev = NULL;
hlpfile->next = first_hlpfile;
hlpfile->wRefCount = 1;
@@ -303,6 +307,146 @@ HLPFILE *HLPFILE_ReadHlpFile(LPCSTR lpsz
/***********************************************************************
*
+ * HLPFILE_ReadCntFile
+ *
+ *
+ * NOTE: We could use msvcrt.* functions here (fopen, fgets)
+ * to make life little easier, but we cannot - it breaks
+ * unistd.h included in macro.lex.yy.c file.
+ */
+static HLPFILE_CNT* HLPFILE_ReadCntFile(LPCSTR lpszPath)
+{
+ char *str, *next_str;
+ char *buf;
+ int l, len, read;
+ HLPFILE_CNT *entry, *cur, *ret=NULL;
+ HANDLE h;
+
+ h = CreateFile(lpszPath, GENERIC_READ, FILE_SHARE_READ,
+ NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
+ if (h == INVALID_HANDLE_VALUE) return NULL;
+
+ len = GetFileSize(h, NULL);
+ if (len == INVALID_FILE_SIZE)
+ {
+ CloseHandle(h);
+ return ret;
+ }
+ buf = HeapAlloc(GetProcessHeap(), 0, len);
+ if (!buf)
+ {
+ CloseHandle(h);
+ return ret;
+ }
+ if (!ReadFile(h, buf, len, &read, NULL))
+ {
+ CloseHandle(h);
+ HeapFree(GetProcessHeap(), 0, buf);
+ return ret;
+ }
+ CloseHandle(h);
+ str = buf;
+ cur = NULL;
+ while (str)
+ {
+ char *start, *end;
+
+ next_str = strchr(str, '\n');
+ if (next_str)
+ {
+ end = next_str-1;
+ while (end > str && isspace(*end)) *end--=0;
+ next_str++;
+ }
+
+ start = str;
+ while (isspace(*start)) start++;
+ if (*start == ':' || *start == 0)
+ {
+ str = next_str;
+ continue;
+ }
+ entry = HeapAlloc(GetProcessHeap(), 0, sizeof(HLPFILE_CNT));
+ entry->lpszTitle = NULL;
+ entry->lpszPath = NULL;
+ entry->lpszWindow = NULL;
+ entry->buf = HeapAlloc(GetProcessHeap(), 0, strlen(start)+1);
+ strcpy(entry->buf, start);
+ start = entry->buf;
+ sscanf(start, "%d", &l);
+ while (isdigit(*start)) start++;
+ while (isspace(*start)) start++;
+ entry->lpszTitle = start;
+ end = strchr(start, '=');
+ if (end)
+ {
+ *end = 0;
+ start = end+1;
+ end = strchr(start, '@');
+ if (end)
+ {
+ *end = 0;
+ end++;
+ entry->lpszPath = end;
+ end = strchr(entry->lpszPath, '>');
+ if (end)
+ {
+ entry->lpszWindow = end+1;
+ *end = 0;
+ }
+ }
+ entry->lHash = HLPFILE_Hash(start);
+ }
+ entry->level = l;
+ entry->next = NULL;
+ entry->child = NULL;
+ entry->parent = NULL;
+ while (cur && cur->level > entry->level) cur = cur->parent;
+ if (cur)
+ {
+ if (cur->level == entry->level) /* level exists */
+ {
+ entry->parent = cur->parent;
+ cur->next = entry;
+ }
+ else /* entry on new level */
+ {
+ entry->parent = cur;
+ cur->child = entry;
+ }
+ }
+ cur = entry;
+ if (!ret) ret = cur;
+ str = next_str;
+ WINE_TRACE("Adding entry %p l: %d, t: %s, h: %.08X, f: %s\n",
+ entry, entry->level, entry->lpszTitle, entry->lHash, entry->lpszPath);
+ }
+ HeapFree(GetProcessHeap(), 0, buf);
+ return ret;
+}
+
+
+/***********************************************************************
+ *
+ * HLPFILE_FreeCnt
+ */
+static void HLPFILE_FreeCnt(HLPFILE_CNT *cnt)
+{
+ HLPFILE_CNT *p;
+
+ WINE_FIXME("%s\n", cnt->buf);
+ while (cnt)
+ {
+ HLPFILE_FreeCnt(cnt->child);
+ HeapFree(GetProcessHeap(), 0, cnt->buf);
+ p = cnt->next;
+ HeapFree(GetProcessHeap(), 0, cnt);
+ cnt = p;
+ }
+}
+
+/***********************************************************************
+ *
* HLPFILE_DoReadHlpFile
*/
static BOOL HLPFILE_DoReadHlpFile(HLPFILE *hlpfile, LPCSTR lpszPath)
@@ -373,6 +517,7 @@ static BOOL HLPFILE_DoReadHlpFile(HLPFIL
} while (ref != 0xffffffff);
HLPFILE_GetMap(hlpfile);
+ hlpfile->cnt = HLPFILE_ReadCntFile(hlpfile->lpszCntPath);
return HLPFILE_GetContext(hlpfile);
}
@@ -1367,8 +1512,10 @@ static BOOL HLPFILE_SystemCommands(HLPFI
HLPFILE_MACRO *macro, **m;
LPSTR p;
unsigned short magic, minor, major, flags;
+ int len;
hlpfile->lpszTitle = NULL;
+ hlpfile->lpszCntPath = NULL;
if (!HLPFILE_FindSubFile("|SYSTEM", &buf, &end)) return FALSE;
@@ -1467,12 +1614,33 @@ static BOOL HLPFILE_SystemCommands(HLPFI
wi->size.cx, wi->size.cy);
}
break;
+ case 10:
+ len = strlen(hlpfile->lpszPath);
+ if (hlpfile->lpszCntPath) {WINE_WARN("cnt\n"); break;}
+ hlpfile->lpszCntPath = HeapAlloc(GetProcessHeap(), 0, len + 1);
+ if (!hlpfile->lpszCntPath) return FALSE;
+ lstrcpy(hlpfile->lpszCntPath, hlpfile->lpszPath);
+ hlpfile->lpszCntPath[len-3] = 'C';
+ hlpfile->lpszCntPath[len-2] = 'N';
+ hlpfile->lpszCntPath[len-1] = 'T';
+ WINE_TRACE("CNT: '%s'\n", hlpfile->lpszCntPath);
+ break;
default:
WINE_WARN("Unsupported SystemRecord[%d]\n", GET_USHORT(ptr, 0));
}
}
if (!hlpfile->lpszTitle)
hlpfile->lpszTitle = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 1);
+ if (!hlpfile->lpszCntPath)
+ {
+ len = strlen(hlpfile->lpszPath);
+ hlpfile->lpszCntPath = HeapAlloc(GetProcessHeap(), 0, len+1);
+ lstrcpy(hlpfile->lpszCntPath, hlpfile->lpszPath);
+ hlpfile->lpszCntPath[len-3] = 'C';
+ hlpfile->lpszCntPath[len-2] = 'N';
+ hlpfile->lpszCntPath[len-1] = 'T';
+ WINE_TRACE("CNT not found, assuming '%s'\n", hlpfile->lpszCntPath);
+ }
return TRUE;
}
@@ -2054,6 +2222,8 @@ void HLPFILE_FreeHlpFile(HLPFILE* hlpfil
HLPFILE_DeleteMacro(hlpfile->first_macro);
if (hlpfile->numWindows) HeapFree(GetProcessHeap(), 0, hlpfile->windows);
+ HLPFILE_FreeCnt(hlpfile->cnt);
+ HeapFree(GetProcessHeap(), 0, hlpfile->lpszCntPath);
HeapFree(GetProcessHeap(), 0, hlpfile->Context);
HeapFree(GetProcessHeap(), 0, hlpfile->Map);
HeapFree(GetProcessHeap(), 0, hlpfile->lpszTitle);
diff --git a/programs/winhelp/hlpfile.h b/programs/winhelp/hlpfile.h
index 4d62cdd..473b8ab 100644
--- a/programs/winhelp/hlpfile.h
+++ b/programs/winhelp/hlpfile.h
@@ -121,11 +121,25 @@ typedef struct
COLORREF color;
} HLPFILE_FONT;
+typedef struct tagHlpFileCnt
+{
+ LPSTR lpszTitle;
+ LPSTR lpszPath;
+ LPSTR lpszWindow;
+ LPSTR buf;
+ LONG lHash;
+ int level;
+ struct tagHlpFileCnt *next;
+ struct tagHlpFileCnt *parent;
+ struct tagHlpFileCnt *child;
+} HLPFILE_CNT;
+
typedef struct tagHlpFileFile
{
LPSTR lpszPath;
LPSTR lpszTitle;
LPSTR lpszCopyright;
+ LPSTR lpszCntPath;
HLPFILE_PAGE* first_page;
HLPFILE_MACRO* first_macro;
unsigned wContextLen;
@@ -134,6 +148,8 @@ typedef struct tagHlpFileFile
HLPFILE_MAP* Map;
unsigned long contents_start;
+ HLPFILE_CNT* cnt;
+
struct tagHlpFileFile* prev;
struct tagHlpFileFile* next;
More information about the wine-patches
mailing list