Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

435 lines
14 KiB

/*++
Copyright (c) 1996 Microsoft Corporation
Module Name:
writentf.c
Abstract:
Write a NTF file.
Environment:
Windows NT PostScript driver.
Revision History:
07/08/98 -ksuzuki-
Modified to support -v(verbose) and -o(optimize) options.
11/21/96 -slam-
Created.
dd-mm-yy -author-
description
--*/
#include "writentf.h"
extern bVerbose;
extern bOptimize;
int __cdecl compareGlyphSet(const void *elem1, const void *elem2)
{
PGLYPHSETDATA *p1;
PGLYPHSETDATA *p2;
PGLYPHSETDATA pGlyphSet1;
PGLYPHSETDATA pGlyphSet2;
DWORD hashValue1, hashValue2;
p1 = (PGLYPHSETDATA*)elem1;
p2 = (PGLYPHSETDATA*)elem2;
pGlyphSet1 = *p1;
pGlyphSet2 = *p2;
hashValue1 = HashKeyword(MK_PTR(pGlyphSet1, dwGlyphSetNameOffset));
hashValue2 = HashKeyword(MK_PTR(pGlyphSet2, dwGlyphSetNameOffset));
if (hashValue1 == hashValue2)
return(0);
else if (hashValue1 < hashValue2)
return(-1);
else
return(1);
}
int __cdecl compareFontMtx(const void *elem1, const void *elem2)
{
PNTM *p1;
PNTM *p2;
PNTM pNTM1;
PNTM pNTM2;
DWORD hashValue1, hashValue2;
p1 = (PNTM*)elem1;
p2 = (PNTM*)elem2;
pNTM1 = *p1;
pNTM2 = *p2;
hashValue1 = HashKeyword(MK_PTR(pNTM1, dwFontNameOffset));
hashValue2 = HashKeyword(MK_PTR(pNTM2, dwFontNameOffset));
if (hashValue1 == hashValue2)
return(0);
else if (hashValue1 < hashValue2)
return(-1);
else
return(1);
}
BOOL
WriteNTF(
IN PWSTR pwszNTFFile,
IN DWORD dwGlyphSetCount,
IN DWORD dwGlyphSetTotalSize,
IN PGLYPHSETDATA *pGlyphSetData,
IN DWORD dwFontMtxCount,
IN DWORD dwFontMtxTotalSize,
IN PNTM *pNTM
)
{
HANDLE hNTFFile;
NTF_FILEHEADER fileHeader;
PNTF_GLYPHSETENTRY pGlyphSetEntry;
PNTF_FONTMTXENTRY pFontMtxEntry;
ULONG ulGlyphSetEntrySize;
ULONG ulFontMtxEntrySize;
ULONG ulByteWritten;
ULONG i, j;
DWORD dwOffset;
DWORD dwGlyphSetCount2, dwGlyphSetTotalSize2;
PGLYPHSETDATA pgsd;
DWORD dwEofMark = NTF_EOF_MARK;
dwGlyphSetCount2 = dwGlyphSetTotalSize2 = 0;
//
// Count the number of glyphsets necessary or referenced and their total
// size. When optimization option is specified, don't count the glyphsets
// without reference mark.
//
for (i = 0; i < dwGlyphSetCount; i++)
{
if (!bOptimize || pGlyphSetData[i]->dwReserved[0])
{
dwGlyphSetCount2++;
dwGlyphSetTotalSize2 += pGlyphSetData[i]->dwSize;
}
}
if (!bOptimize && (dwGlyphSetTotalSize != dwGlyphSetTotalSize2))
{
ERR(("WriteNTF:total size mismatch on optimization\n"));
return FALSE;
}
if (bVerbose)
{
printf("Number of glyphset:%ld(total:%ld)\n",
dwGlyphSetCount, dwGlyphSetTotalSize);
if (bOptimize)
{
printf("Number of glyphset referenced:%ld(total:%ld)\n",
dwGlyphSetCount2, dwGlyphSetTotalSize2);
}
printf("Number of font matrix:%ld(total:%ld)\n",
dwFontMtxCount, dwFontMtxTotalSize);
printf("\n");
}
// Fill in NTF file header.
fileHeader.dwSignature = NTF_FILE_MAGIC;
fileHeader.dwDriverType = NTF_DRIVERTYPE_PS;
fileHeader.dwVersion = NTF_VERSION_NUMBER;
for (i = 0; i < 5; i++)
fileHeader.dwReserved[i] = 0;
fileHeader.dwGlyphSetCount = dwGlyphSetCount2;
fileHeader.dwFontMtxCount = dwFontMtxCount;
ulGlyphSetEntrySize = dwGlyphSetCount2 * sizeof(NTF_GLYPHSETENTRY);
ulFontMtxEntrySize = dwFontMtxCount * sizeof(NTF_FONTMTXENTRY);
fileHeader.dwGlyphSetOffset = sizeof(NTF_FILEHEADER);
fileHeader.dwFontMtxOffset = fileHeader.dwGlyphSetOffset + ulGlyphSetEntrySize;
// Fill in glyph set entries.
qsort(pGlyphSetData, dwGlyphSetCount, sizeof(PGLYPHSETDATA), compareGlyphSet);
pGlyphSetEntry = MemAllocZ(ulGlyphSetEntrySize);
if (!pGlyphSetEntry)
{
ERR(("WriteNTF:MemAllocZ\n"));
return(FALSE);
}
dwOffset = fileHeader.dwFontMtxOffset + ulFontMtxEntrySize;
for (i = j = 0; i < dwGlyphSetCount; i++)
{
pgsd = pGlyphSetData[i];
// If no refernce mark is set with optimization option, ignore this
// glyphset data.
if (bOptimize && !(pgsd->dwReserved[0]))
{
pgsd = NULL;
}
if (pgsd)
{
pGlyphSetEntry[j].dwNameOffset = dwOffset + pgsd->dwGlyphSetNameOffset;
pGlyphSetEntry[j].dwHashValue = HashKeyword(MK_PTR(pgsd, dwGlyphSetNameOffset));
pGlyphSetEntry[j].dwDataSize = pgsd->dwSize;
pGlyphSetEntry[j].dwDataOffset = dwOffset;
pGlyphSetEntry[j].dwGlyphSetType = 0;
pGlyphSetEntry[j].dwFlags = 0;
pGlyphSetEntry[j].dwReserved[0] = 0;
pGlyphSetEntry[j].dwReserved[1] = 0;
dwOffset += pgsd->dwSize;
j++;
}
}
// Fill in font metrics entries.
qsort(pNTM, dwFontMtxCount, sizeof(PNTM), compareFontMtx);
pFontMtxEntry = MemAllocZ(ulFontMtxEntrySize);
if (!pFontMtxEntry)
{
ERR(("WriteNTF:MemAllocZ\n"));
MemFree(pGlyphSetEntry);
return(FALSE);
}
if (dwOffset != (fileHeader.dwFontMtxOffset +
ulFontMtxEntrySize +
dwGlyphSetTotalSize2))
{
ERR(("WriteNTF:dwOffset\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
return(FALSE);
}
for (i = 0; i < dwFontMtxCount; i++)
{
pFontMtxEntry[i].dwFontNameOffset = dwOffset + pNTM[i]->dwFontNameOffset;
pFontMtxEntry[i].dwHashValue = HashKeyword(MK_PTR(pNTM[i], dwFontNameOffset));
pFontMtxEntry[i].dwDataSize = pNTM[i]->dwSize;
pFontMtxEntry[i].dwDataOffset = dwOffset;
pFontMtxEntry[i].dwVersion = 0;
pFontMtxEntry[i].dwReserved[0] = 0;
pFontMtxEntry[i].dwReserved[1] = 0;
pFontMtxEntry[i].dwReserved[2] = 0;
dwOffset += pNTM[i]->dwSize;
}
//
// Begin to write everything into the NTF file!
//
hNTFFile = CreateFile(pwszNTFFile, GENERIC_WRITE, FILE_SHARE_READ, NULL,
CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if (hNTFFile == INVALID_HANDLE_VALUE)
{
ERR(("WriteNTF:CreateFile\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
return(FALSE);
}
if (!WriteFile(hNTFFile, (LPVOID)&fileHeader, sizeof(NTF_FILEHEADER),
(LPDWORD)&ulByteWritten, (LPOVERLAPPED)NULL)
|| (ulByteWritten != sizeof(NTF_FILEHEADER)))
{
ERR(("WriteNTF:WriteFile\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return(FALSE);
}
if (bVerbose)
{
char s[5];
s[0] = (char)(fileHeader.dwSignature >> 24);
s[1] = (char)(fileHeader.dwSignature >> 16);
s[2] = (char)(fileHeader.dwSignature >> 8);
s[3] = (char)(fileHeader.dwSignature );
s[4] = '\0';
printf("NTF_FILEHEADER:dwSignature:%08X('%s')\n", fileHeader.dwSignature, s);
s[0] = (char)(fileHeader.dwDriverType >> 24);
s[1] = (char)(fileHeader.dwDriverType >> 16);
s[2] = (char)(fileHeader.dwDriverType >> 8);
s[3] = (char)(fileHeader.dwDriverType );
s[4] = '\0';
printf("NTF_FILEHEADER:dwDriverType:%08X('%s')\n", fileHeader.dwDriverType, s);
printf("NTF_FILEHEADER:dwVersion:%08X\n", fileHeader.dwVersion);
printf("NTF_FILEHEADER:dwGlyphSetCount:%ld\n", fileHeader.dwGlyphSetCount);
printf("NTF_FILEHEADER:dwFontMtxCount:%ld\n", fileHeader.dwFontMtxCount);
printf("\n");
}
if (!WriteFile(hNTFFile, (LPVOID)pGlyphSetEntry, ulGlyphSetEntrySize,
(LPDWORD)&ulByteWritten, (LPOVERLAPPED)NULL)
|| (ulByteWritten != ulGlyphSetEntrySize))
{
ERR(("WriteNTF:WriteFile\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return(FALSE);
}
if (bVerbose)
{
for (i = 0; i < dwGlyphSetCount2; i++)
{
printf("NTF_GLYPHSETENTRY for GLYPHSETDATA #%d\n", i + 1);
printf("NTF_GLYPHSETENTRY:dwHashValue:%08X\n", pGlyphSetEntry[i].dwHashValue);
printf("NTF_GLYPHSETENTRY:dwDataSize:%ld\n", pGlyphSetEntry[i].dwDataSize);
printf("\n");
}
}
if (!WriteFile(hNTFFile, (LPVOID)pFontMtxEntry, ulFontMtxEntrySize,
(LPDWORD)&ulByteWritten, (LPOVERLAPPED)NULL)
|| (ulByteWritten != ulFontMtxEntrySize))
{
ERR(("WriteNTF:WriteFile\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return(FALSE);
}
if (bVerbose)
{
for (i = 0; i < dwFontMtxCount; i++)
{
printf("NTF_FONTMTXENTRY for NTM #%d\n", i + 1);
printf("NTF_FONTMTXENTRY:dwHashValue:%08X\n", pFontMtxEntry[i].dwHashValue);
printf("NTF_FONTMTXENTRY:dwDataSize:%ld\n", pFontMtxEntry[i].dwDataSize);
printf("NTF_FONTMTXENTRY:dwVersion:%08X\n", pFontMtxEntry[i].dwVersion);
printf("\n");
}
}
for (i = j = 0; i < dwGlyphSetCount; i++)
{
pgsd = pGlyphSetData[i];
// If no refernce mark is set with optimization option, ignore this
// glyphset data.
if (bOptimize && !(pgsd->dwReserved[0]))
{
pgsd = NULL;
}
if (pgsd)
{
LONG lBytes, lSize = pgsd->dwSize;
PBYTE pTemp = (PBYTE)pgsd;
pgsd->dwReserved[0] = 0; // Make sure it's cleared always.
while (lSize > 0)
{
lBytes = (lSize > 20000) ? 20000 : lSize;
if (!WriteFile(hNTFFile, (LPVOID)pTemp, lBytes,
(LPDWORD)&ulByteWritten, (LPOVERLAPPED)NULL)
|| (ulByteWritten != (ULONG)lBytes))
{
ERR(("WriteNTF:WriteFile\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return(FALSE);
}
lSize -= 20000;
pTemp += 20000;
}
}
if (bVerbose && pgsd)
{
printf("GLYPHSETDATA #%d\n", j++ + 1);
printf("GLYPHSETDATA:dwSize:%ld\n", pgsd->dwSize);
printf("GLYPHSETDATA:dwVersion:%08X\n", pgsd->dwVersion);
printf("GLYPHSETDATA:dwFlags:%08X\n", pgsd->dwFlags);
printf("GLYPHSETDATA:dwGlyphSetNameOffset:%s\n", (PSZ)MK_PTR(pgsd, dwGlyphSetNameOffset));
printf("GLYPHSETDATA:dwGlyphCount:%ld\n", pgsd->dwGlyphCount);
printf("GLYPHSETDATA:dwRunCount:%ld\n", pgsd->dwRunCount);
printf("GLYPHSETDATA:dwCodePageCount:%ld\n", pgsd->dwCodePageCount);
printf("\n");
}
}
for (i = 0; i < dwFontMtxCount; i++)
{
if (!WriteFile(hNTFFile, (LPVOID)pNTM[i], pNTM[i]->dwSize,
(LPDWORD)&ulByteWritten, (LPOVERLAPPED)NULL)
|| (ulByteWritten != pNTM[i]->dwSize))
{
ERR(("WriteNTF:WriteFile\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return(FALSE);
}
if (bVerbose)
{
printf("NTM #%d\n", i + 1);
printf("NTM:dwSize:%ld\n", pNTM[i]->dwSize);
printf("NTM:dwVersion:%08X\n", pNTM[i]->dwVersion);
printf("NTM:dwFlags:%08X\n", pNTM[i]->dwFlags);
printf("NTM:dwFontNameOffset:%s\n", (PSZ)MK_PTR(pNTM[i], dwFontNameOffset));
printf("NTM:dwDisplayNameOffset:%S\n", (PTSTR)MK_PTR(pNTM[i], dwDisplayNameOffset));
printf("NTM:dwFontVersion:%08X\n", pNTM[i]->dwFontVersion);
printf("NTM:dwGlyphSetNameOffset:%s\n", (PSZ)MK_PTR(pNTM[i], dwGlyphSetNameOffset));
printf("NTM:dwGlyphCount:%ld\n", pNTM[i]->dwGlyphCount);
printf("NTM:dwCharWidthCount:%ld\n", pNTM[i]->dwCharWidthCount);
printf("NTM:dwDefaultCharWidth:%ld\n", pNTM[i]->dwDefaultCharWidth);
printf("NTM:dwKernPairCount:%ld\n", pNTM[i]->dwKernPairCount);
printf("NTM:dwCharSet:%ld\n", pNTM[i]->dwCharSet);
printf("NTM:dwCodePage:%ld\n", pNTM[i]->dwCodePage);
printf("\n");
}
}
//
// Write EOF marker
//
if (!WriteFile(hNTFFile, (LPVOID)&dwEofMark, sizeof (DWORD),
(LPDWORD)&ulByteWritten, (LPOVERLAPPED)NULL)
|| (ulByteWritten != sizeof (DWORD)))
{
ERR(("WriteNTF:WriteFile:EOF\n"));
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return (FALSE);
}
MemFree(pGlyphSetEntry);
MemFree(pFontMtxEntry);
CloseHandle(hNTFFile);
return(TRUE);
}