Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
/* Copyright (C) 2002 Aladdin Enterprises.  All rights reserved.
2
 
3
  This software is provided AS-IS with no warranty, either express or
4
  implied.
5
 
6
  This software is distributed under license and may not be copied,
7
  modified or distributed except as expressly authorized under the terms
8
  of the license contained in the file LICENSE in this distribution.
9
 
10
  For more information about licensing, please refer to
11
  http://www.ghostscript.com/licensing/. For information on
12
  commercial licensing, go to http://www.artifex.com/licensing/ or
13
  contact Artifex Software, Inc., 101 Lucas Valley Road #110,
14
  San Rafael, CA  94903, U.S.A., +1(415)492-9861.
15
*/
16
 
17
/* $Id: gxfcopy.c,v 1.55 2004/12/15 23:21:32 igor Exp $ */
18
/* Font copying for high-level output */
19
#include "memory_.h"
20
#include "gx.h"
21
#include "gscencs.h"
22
#include "gserrors.h"
23
#include "gsline.h"		/* for BuildChar */
24
#include "gspaint.h"		/* for BuildChar */
25
#include "gspath.h"		/* for gs_moveto in BuildChar */
26
#include "gsstruct.h"
27
#include "gsutil.h"
28
#include "stream.h"
29
#include "gxfont.h"
30
#include "gxfont1.h"
31
#include "gxfont42.h"
32
#include "gxfcid.h"
33
#include "gxfcopy.h"
34
#include "gxfcache.h"		/* for gs_font_dir_s */
35
#include "gxistate.h"		/* for Type 1 glyph_outline */
36
#include "gxtext.h"		/* for BuildChar */
37
#include "gxtype1.h"		/* for Type 1 glyph_outline */
38
#include "gzstate.h"		/* for path for BuildChar */
39
#include "gdevpsf.h"
40
 
41
#define GLYPHS_SIZE_IS_PRIME 1 /* Old code = 0, new code = 1. */
42
 
43
/* ================ Types and structures ================ */
44
 
45
typedef struct gs_copied_glyph_s gs_copied_glyph_t;
46
typedef struct gs_copied_font_data_s gs_copied_font_data_t;
47
 
48
typedef struct gs_copied_font_procs_s {
49
    int (*finish_copy_font)(gs_font *font, gs_font *copied);
50
    int (*copy_glyph)(gs_font *font, gs_glyph glyph, gs_font *copied,
51
		      int options);
52
    int (*add_encoding)(gs_font *copied, gs_char chr, gs_glyph glyph);
53
    int (*named_glyph_slot)(gs_copied_font_data_t *cfdata, gs_glyph glyph,
54
			    gs_copied_glyph_t **pslot);
55
    /* Font procedures */
56
    font_proc_encode_char((*encode_char));
57
    font_proc_glyph_info((*glyph_info));
58
    font_proc_glyph_outline((*glyph_outline));
59
} gs_copied_font_procs_t;
60
 
61
/*
62
 * We need to store the Subrs data for Type 1/2 and CIDFontType 0 fonts,
63
 * and the GlobalSubrs data for all but Type 1.
64
 */
65
typedef struct gs_subr_info_s {
66
    byte *data;		/* Subr data */
67
    int count;
68
    uint *starts;	/* [count+1] Subr[i] = data[starts[i]..starts[i+1]] */
69
} gs_subr_info_t;
70
 
71
/*
72
 * The glyphs for copied fonts are stored explicitly in a table indexed by
73
 * glyph number.
74
 * For Type 1 fonts, the glyph numbers are parallel to the hashed name table.
75
 * For TrueType fonts, the glyph number is the TrueType GID.
76
 * For CIDFontType 0 fonts, the glyph number is the CID.
77
 * For CIDFontType 2 fonts, the glyph number is the TrueType GID;
78
 * a separate CIDMap array maps CIDs to GIDs.
79
 */
80
struct gs_copied_glyph_s {
81
    gs_const_string gdata;	/* vector data */
82
#define HAS_DATA 1		/* entry is in use */
83
				/* HAS_SBW* are only used for TT-based fonts */
84
#define HAS_SBW0 2		/* has hmtx */
85
#define HAS_SBW1 4		/* has vmtx */
86
    byte used;			/* non-zero iff this entry is in use */
87
				/* (if not, gdata.{data,size} = 0) */
88
};
89
/*
90
 * We use a special GC descriptor to avoid large GC overhead.
91
 */
92
gs_private_st_composite(st_gs_copied_glyph_element, gs_copied_glyph_t,
93
			"gs_copied_glyph_t[]", copied_glyph_element_enum_ptrs,
94
			copied_glyph_element_reloc_ptrs);
95
private ENUM_PTRS_WITH(copied_glyph_element_enum_ptrs, gs_copied_glyph_t *pcg)
96
     if (index < size / (uint)sizeof(gs_copied_glyph_t))
97
	 return ENUM_CONST_STRING(&pcg[index].gdata);
98
     return 0;
99
ENUM_PTRS_END
100
private RELOC_PTRS_WITH(copied_glyph_element_reloc_ptrs, gs_copied_glyph_t *pcg)
101
{
102
    uint count = size / (uint)sizeof(gs_copied_glyph_t);
103
    gs_copied_glyph_t *p = pcg;
104
 
105
    for (; count > 0; --count, ++p)
106
	if (p->gdata.size > 0)
107
	    RELOC_CONST_STRING_VAR(p->gdata);
108
}
109
RELOC_PTRS_END
110
 
111
/*
112
 * Type 1 and TrueType fonts also have a 'names' table, parallel to the
113
 * 'glyphs' table.
114
 * For Type 1 fonts, this is a hash table; glyph numbers are assigned
115
 * arbitrarily, according to the hashed placement of the names.
116
 * For TrueType fonts, this is indexed by GID.
117
 * The strings in this table are either those returned by the font's
118
 * glyph_name procedure, which we assume are garbage-collected, or those
119
 * associated with the known encodings, which we assume are immutable.
120
 */
121
typedef struct gs_copied_glyph_name_s {
122
    gs_glyph glyph;		/* key (for comparison and glyph_name only) */
123
    gs_const_string str;	/* glyph name */
124
} gs_copied_glyph_name_t;
125
/*
126
 * We use the same special GC descriptor as above for 'names'.
127
 */
128
gs_private_st_composite(st_gs_copied_glyph_name_element,
129
			gs_copied_glyph_name_t,
130
			"gs_copied_glyph_name_t[]",
131
			copied_glyph_name_enum_ptrs,
132
			copied_glyph_name_reloc_ptrs);
133
private ENUM_PTRS_WITH(copied_glyph_name_enum_ptrs, gs_copied_glyph_name_t *pcgn)
134
     if (index < size / (uint)sizeof(gs_copied_glyph_name_t)) {
135
	 const gs_copied_glyph_name_t *const p = &pcgn[index];
136
 
137
	 return (p->str.size == 0 ||
138
		 gs_is_c_glyph_name(p->str.data, p->str.size) ?
139
		 ENUM_CONST_STRING2(0, 0) :
140
		 ENUM_CONST_STRING(&p->str));
141
     }
142
     return 0;
143
     /* We should mark glyph name here, but we have no access to 
144
        the gs_font_dir instance. Will mark in gs_copied_font_data_enum_ptrs.
145
      */
146
ENUM_PTRS_END
147
private RELOC_PTRS_WITH(copied_glyph_name_reloc_ptrs, gs_copied_glyph_name_t *pcgn)
148
{
149
    uint count = size / (uint)sizeof(gs_copied_glyph_name_t);
150
    gs_copied_glyph_name_t *p = pcgn;
151
 
152
    for (; count > 0; --count, ++p)
153
	if (p->str.size > 0 && !gs_is_c_glyph_name(p->str.data, p->str.size))
154
	    RELOC_CONST_STRING_VAR(p->str);
155
}
156
RELOC_PTRS_END
157
 
158
/*
159
 * To accommodate glyphs with multiple names, there is an additional
160
 * 'extra_names' table.  Since this is rare, this table uses linear search.
161
 */
162
typedef struct gs_copied_glyph_extra_name_s gs_copied_glyph_extra_name_t;
163
struct gs_copied_glyph_extra_name_s {
164
    gs_copied_glyph_name_t name;
165
    uint gid;			/* index in glyphs table */
166
    gs_copied_glyph_extra_name_t *next;
167
};
168
BASIC_PTRS(gs_copied_glyph_extra_name_ptrs) {
169
    GC_STRING_ELT(gs_copied_glyph_extra_name_t, name.str),
170
    GC_OBJ_ELT(gs_copied_glyph_extra_name_t, next)
171
};
172
gs_private_st_basic(st_gs_copied_glyph_extra_name,
173
		    gs_copied_glyph_extra_name_t,
174
		    "gs_copied_glyph_extra_name_t",
175
		    gs_copied_glyph_extra_name_ptrs,
176
		    gs_copied_glyph_extra_name_data);
177
 
178
/*
179
 * The client_data of copied fonts points to an instance of
180
 * gs_copied_font_data_t.
181
 */
182
struct gs_copied_font_data_s {
183
    gs_font_info_t info;	/* from the original font, must be first */
184
    const gs_copied_font_procs_t *procs;
185
    gs_copied_glyph_t *glyphs;	/* [glyphs_size] */
186
    uint glyphs_size;		/* (a power of 2 or a prime number for Type 1/2) */
187
    uint num_glyphs;		/* The number of glyphs copied. */
188
    gs_glyph notdef;		/* CID 0 or .notdef glyph */
189
    /*
190
     * We don't use a union for the rest of the data, because some of the
191
     * cases overlap and it's just not worth the trouble.
192
     */
193
    gs_copied_glyph_name_t *names; /* (Type 1/2, TrueType) [glyphs_size] */
194
    gs_copied_glyph_extra_name_t *extra_names; /* (TrueType) */
195
    byte *data;			/* (TrueType and CID fonts) copied data */
196
    uint data_size;		/* (TrueType and CID fonts) */
197
    gs_glyph *Encoding;		/* (Type 1/2 and Type 42) [256] */
198
    ushort *CIDMap;		/* (CIDFontType 2) [CIDCount] */
199
    gs_subr_info_t subrs;	/* (Type 1/2 and CIDFontType 0) */
200
    gs_subr_info_t global_subrs; /* (Type 2 and CIDFontType 0) */
201
    gs_font_cid0 *parent;	/* (Type 1 subfont) => parent CIDFontType 0 */
202
    gs_font_dir *dir;
203
};
204
extern_st(st_gs_font_info);
205
private 
206
ENUM_PTRS_WITH(gs_copied_font_data_enum_ptrs, gs_copied_font_data_t *cfdata)
207
    if (index == 12) {
208
	gs_copied_glyph_name_t *names = cfdata->names;
209
	gs_copied_glyph_extra_name_t *en = cfdata->extra_names;
210
	int i;
211
 
212
	if (names != NULL)
213
	    for (i = 0; i < cfdata->glyphs_size; ++i)
214
		if (names[i].glyph < gs_c_min_std_encoding_glyph)
215
		    cfdata->dir->ccache.mark_glyph(mem, names[i].glyph, NULL);
216
	for (; en != NULL; en = en->next)
217
	    if (en->name.glyph < gs_c_min_std_encoding_glyph)
218
		cfdata->dir->ccache.mark_glyph(mem, en->name.glyph, NULL);
219
    }
220
    return ENUM_USING(st_gs_font_info, &cfdata->info, sizeof(gs_font_info_t), index - 12);
221
    ENUM_PTR3(0, gs_copied_font_data_t, glyphs, names, extra_names);
222
    ENUM_PTR3(3, gs_copied_font_data_t, data, Encoding, CIDMap);
223
    ENUM_PTR3(6, gs_copied_font_data_t, subrs.data, subrs.starts, global_subrs.data);
224
    ENUM_PTR3(9, gs_copied_font_data_t, global_subrs.starts, parent, dir);
225
ENUM_PTRS_END
226
 
227
private RELOC_PTRS_WITH(gs_copied_font_data_reloc_ptrs, gs_copied_font_data_t *cfdata)
228
{
229
    RELOC_PTR3(gs_copied_font_data_t, glyphs, names, extra_names);
230
    RELOC_PTR3(gs_copied_font_data_t, data, Encoding, CIDMap);
231
    RELOC_PTR3(gs_copied_font_data_t, subrs.data, subrs.starts, global_subrs.data);
232
    RELOC_PTR3(gs_copied_font_data_t, global_subrs.starts, parent, dir);
233
    RELOC_USING(st_gs_font_info, &cfdata->info, sizeof(gs_font_info_t));
234
}
235
RELOC_PTRS_END
236
 
237
gs_private_st_composite(st_gs_copied_font_data, gs_copied_font_data_t, "gs_copied_font_data_t",\
238
    gs_copied_font_data_enum_ptrs, gs_copied_font_data_reloc_ptrs);
239
 
240
inline private gs_copied_font_data_t *
241
cf_data(const gs_font *font)
242
{
243
    return (gs_copied_font_data_t *)font->client_data;
244
}
245
 
246
/* ================ Procedures ================ */
247
 
248
/* ---------------- Private utilities ---------------- */
249
 
250
/* Copy a string.  Return 0 or gs_error_VMerror. */
251
private int
252
copy_string(gs_memory_t *mem, gs_const_string *pstr, client_name_t cname)
253
{
254
    const byte *data = pstr->data;
255
    uint size = pstr->size;
256
    byte *str;
257
 
258
    if (data == 0)
259
	return 0;		/* empty string */
260
    str = gs_alloc_string(mem, size, cname);
261
    pstr->data = str;
262
    if (str == 0)
263
	return_error(gs_error_VMerror);
264
    memcpy(str, data, size);
265
    return 0;
266
}
267
 
268
/* Free a copied string. */
269
private void
270
uncopy_string(gs_memory_t *mem, gs_const_string *pstr, client_name_t cname)
271
{
272
    if (pstr->data)
273
	gs_free_const_string(mem, pstr->data, pstr->size, cname);
274
}
275
 
276
/*
277
 * Allocate an Encoding for a Type 1 or Type 42 font.
278
 */
279
private int
280
copied_Encoding_alloc(gs_font *copied)
281
{
282
    gs_copied_font_data_t *const cfdata = cf_data(copied);
283
    gs_glyph *Encoding = (gs_glyph *)
284
	gs_alloc_byte_array(copied->memory, 256, sizeof(*cfdata->Encoding),
285
			    "copy_font_type1(Encoding)");
286
    int i;
287
 
288
    if (Encoding == 0)
289
	return_error(gs_error_VMerror);
290
    for (i = 0; i < 256; ++i)
291
	Encoding[i] = GS_NO_GLYPH;
292
    cfdata->Encoding = Encoding;
293
    return 0;
294
}
295
 
296
/*
297
 * Allocate and set up data copied from a TrueType or CID font.
298
 * stell(*s) + extra is the length of the data.
299
 */
300
private int
301
copied_data_alloc(gs_font *copied, stream *s, uint extra, int code)
302
{
303
    gs_copied_font_data_t *const cfdata = cf_data(copied);
304
    uint len = stell(s);
305
    byte *fdata;
306
 
307
    if (code < 0)
308
	return code;
309
    fdata = gs_alloc_bytes(copied->memory, len + extra, "copied_data_alloc");
310
    if (fdata == 0)
311
	return_error(gs_error_VMerror);
312
    swrite_string(s, fdata, len);
313
    cfdata->data = fdata;
314
    cfdata->data_size = len + extra;
315
    return 0;
316
}
317
 
318
/*
319
 * Copy Subrs or GSubrs from a font.
320
 */
321
private int
322
copy_subrs(gs_font_type1 *pfont, bool global, gs_subr_info_t *psi,
323
	   gs_memory_t *mem)
324
{
325
    int i, code;
326
    uint size;
327
    gs_glyph_data_t gdata;
328
    byte *data;
329
    uint *starts;
330
 
331
    gdata.memory = pfont->memory;
332
    /* Scan the font to determine the size of the subrs. */
333
    for (i = 0, size = 0;
334
	 (code = pfont->data.procs.subr_data(pfont, i, global, &gdata)) !=
335
	     gs_error_rangecheck;
336
	 ++i) {
337
	if (code >= 0) {
338
	    size += gdata.bits.size;
339
	    gs_glyph_data_free(&gdata, "copy_subrs");
340
	}
341
    }
342
    if (size == 0)
343
	data = 0, starts = 0, i = 0;
344
    else {
345
	/* Allocate the copy. */
346
	data = gs_alloc_bytes(mem, size, "copy_subrs(data)");
347
	starts = (uint *)gs_alloc_byte_array(mem, i + 1, sizeof(*starts),
348
					     "copy_subrs(starts)");
349
	if (data == 0 || starts == 0) {
350
	    gs_free_object(mem, starts, "copy_subrs(starts)");
351
	    gs_free_object(mem, data, "copy_subrs(data)");
352
	    return_error(gs_error_VMerror);
353
	}
354
 
355
	/* Copy the data. */
356
	for (i = 0, size = 0;
357
	     (code = pfont->data.procs.subr_data(pfont, i, global, &gdata)) !=
358
		 gs_error_rangecheck;
359
	     ++i) {
360
	    starts[i] = size;
361
	    if (code >= 0) {
362
		memcpy(data + size, gdata.bits.data, gdata.bits.size);
363
		size += gdata.bits.size;
364
		gs_glyph_data_free(&gdata, "copy_subrs");
365
	    }
366
	}
367
	starts[i] = size;
368
    }
369
 
370
    psi->data = data;
371
    psi->starts = starts;
372
    psi->count = i;
373
    return 0;
374
}
375
 
376
/*
377
 * Return a pointer to the definition of a copied glyph, accessed either by
378
 * name or by glyph number.  If the glyph is out of range, return
379
 * gs_error_rangecheck; if the glyph is in range but undefined, store a
380
 * pointer to the slot where it would be added, which will have gdata.data
381
 * == 0, and return gs_error_undefined; if the glyph is defined, store the
382
 * pointer and return 0.
383
 */
384
private int
385
copied_glyph_slot(gs_copied_font_data_t *cfdata, gs_glyph glyph,
386
		  gs_copied_glyph_t **pslot)
387
{
388
    uint gsize = cfdata->glyphs_size;
389
 
390
    *pslot = 0;
391
    if (glyph >= GS_MIN_GLYPH_INDEX) {
392
	/* CIDFontType 2 uses glyph indices for slots.  */
393
	if (glyph - GS_MIN_GLYPH_INDEX >= gsize)
394
	    return_error(gs_error_rangecheck);
395
	*pslot = &cfdata->glyphs[glyph - GS_MIN_GLYPH_INDEX];
396
    } else if (glyph >= GS_MIN_CID_GLYPH) {
397
	/* CIDFontType 0 uses CIDS for slots.  */
398
	if (glyph - GS_MIN_CID_GLYPH >= gsize)
399
	    return_error(gs_error_rangecheck);
400
	*pslot = &cfdata->glyphs[glyph - GS_MIN_CID_GLYPH];
401
    } else if (cfdata->names == 0)
402
	return_error(gs_error_rangecheck);
403
    else {
404
	int code = cfdata->procs->named_glyph_slot(cfdata, glyph, pslot);
405
 
406
	if (code < 0)
407
	    return code;
408
    }
409
    if (!(*pslot)->used)
410
	return_error(gs_error_undefined);
411
    return 0;
412
}
413
private int
414
named_glyph_slot_none(gs_copied_font_data_t *cfdata, gs_glyph glyph,
415
			gs_copied_glyph_t **pslot)
416
{
417
    return_error(gs_error_rangecheck);
418
}
419
private int
420
named_glyph_slot_hashed(gs_copied_font_data_t *cfdata, gs_glyph glyph,
421
			gs_copied_glyph_t **pslot)
422
{
423
    uint gsize = cfdata->glyphs_size;
424
    gs_copied_glyph_name_t *names = cfdata->names;
425
    uint hash = (uint)glyph % gsize;
426
    /*
427
     * gsize is either a prime number or a power of 2.
428
     * If it is prime, any positive reprobe below gsize guarantees that we
429
     * will touch every slot.
430
     * If it is a power of 2, any odd reprobe guarantees that we
431
     * will touch every slot.
432
     */
433
    uint hash2 = ((uint)glyph / gsize * 2 + 1) % gsize;
434
    uint tries = gsize;
435
 
436
    while (names[hash].str.data != 0 && names[hash].glyph != glyph) {
437
	hash = (hash + hash2) % gsize;
438
	if (!tries)
439
	    return gs_error_undefined;
440
	tries--;
441
    }
442
    *pslot = &cfdata->glyphs[hash];
443
    return 0;
444
}
445
private int
446
named_glyph_slot_linear(gs_copied_font_data_t *cfdata, gs_glyph glyph,
447
			gs_copied_glyph_t **pslot)
448
{
449
    {
450
	gs_copied_glyph_name_t *names = cfdata->names;
451
	int i;
452
 
453
	for (i = 0; i < cfdata->glyphs_size; ++i)
454
	    if (names[i].glyph == glyph) {
455
		*pslot = &cfdata->glyphs[i];
456
		return 0;
457
	    }
458
    }
459
    /* This might be a glyph with multiple names.  Search extra_names. */
460
    {
461
	gs_copied_glyph_extra_name_t *extra_name = cfdata->extra_names;
462
 
463
	for (; extra_name != 0; extra_name = extra_name->next)
464
	    if (extra_name->name.glyph == glyph) {
465
		*pslot = &cfdata->glyphs[extra_name->gid];
466
		return 0;
467
	    }
468
    }
469
    return_error(gs_error_rangecheck);
470
}
471
 
472
/*
473
 * Add glyph data to the glyph table.  This handles copying the vector
474
 * data, detecting attempted redefinitions, and freeing temporary glyph
475
 * data.  The glyph must be an integer, an index in the glyph table.
476
 * Return 1 if the glyph was already defined, 0 if newly added (or an
477
 * error per options).
478
 */
479
private int
480
copy_glyph_data(gs_font *font, gs_glyph glyph, gs_font *copied, int options,
481
		gs_glyph_data_t *pgdata, const byte *prefix, int prefix_bytes)
482
{
483
    gs_copied_font_data_t *const cfdata = cf_data(copied);
484
    uint size = pgdata->bits.size;
485
    gs_copied_glyph_t *pcg = 0;
486
    int code = copied_glyph_slot(cfdata, glyph, &pcg);
487
 
488
    switch (code) {
489
    case 0:			/* already defined */
490
	if ((options & COPY_GLYPH_NO_OLD) ||
491
	    pcg->gdata.size != prefix_bytes + size ||
492
	    memcmp(pcg->gdata.data, prefix, prefix_bytes) ||
493
	    memcmp(pcg->gdata.data + prefix_bytes,
494
		   pgdata->bits.data, size)
495
	    )
496
	    code = gs_note_error(gs_error_invalidaccess);
497
	else
498
	    code = 1;
499
	break;
500
    case gs_error_undefined:
501
	if (options & COPY_GLYPH_NO_NEW)
502
	    code = gs_note_error(gs_error_undefined);
503
	else if (pcg == NULL)
504
	    code = gs_note_error(gs_error_undefined);
505
	else {
506
	    uint str_size = prefix_bytes + size;
507
	    byte *str = gs_alloc_string(copied->memory, str_size,
508
					"copy_glyph_data(data)");
509
 
510
	    if (str == 0)
511
		code = gs_note_error(gs_error_VMerror);
512
	    else {
513
		if (prefix_bytes)
514
		    memcpy(str, prefix, prefix_bytes);
515
		memcpy(str + prefix_bytes, pgdata->bits.data, size);
516
		pcg->gdata.data = str;
517
		pcg->gdata.size = str_size;
518
		pcg->used = HAS_DATA;
519
		code = 0;
520
		cfdata->num_glyphs++;
521
	    }
522
	}
523
    default:
524
	break;
525
    }
526
    gs_glyph_data_free(pgdata, "copy_glyph_data");
527
    return code;
528
}
529
 
530
/*
531
 * Copy a glyph name into the names table.
532
 */
533
private int
534
copy_glyph_name(gs_font *font, gs_glyph glyph, gs_font *copied,
535
		gs_glyph copied_glyph)
536
{
537
    gs_glyph known_glyph;
538
    gs_copied_font_data_t *const cfdata = cf_data(copied);
539
    gs_copied_glyph_t *pcg;
540
    int code = copied_glyph_slot(cfdata, copied_glyph, &pcg);
541
    gs_copied_glyph_name_t *pcgn;
542
    gs_const_string str;
543
 
544
    if (code < 0 ||
545
	(code = font->procs.glyph_name(font, glyph, &str)) < 0
546
	)
547
	return code;
548
    /* Try to share a permanently allocated known glyph name. */
549
    if ((known_glyph = gs_c_name_glyph(str.data, str.size)) != GS_NO_GLYPH)
550
	gs_c_glyph_name(known_glyph, &str);
551
    else if ((code = copy_string(copied->memory, &str, "copy_glyph_name")) < 0)
552
	return code;
553
    pcgn = cfdata->names + (pcg - cfdata->glyphs);
554
    if (pcgn->glyph != GS_NO_GLYPH &&
555
	(pcgn->str.size != str.size ||
556
	 memcmp(pcgn->str.data, str.data, str.size))
557
	) {
558
	/* This is a glyph with multiple names.  Add an extra_name entry. */
559
	gs_copied_glyph_extra_name_t *extra_name =
560
	    gs_alloc_struct(copied->memory, gs_copied_glyph_extra_name_t,
561
			    &st_gs_copied_glyph_extra_name,
562
			    "copy_glyph_name(extra_name)");
563
 
564
	if (extra_name == 0)
565
	    return_error(gs_error_VMerror);
566
	extra_name->next = cfdata->extra_names;
567
	extra_name->gid = pcg - cfdata->glyphs;
568
	cfdata->extra_names = extra_name;
569
	pcgn = &extra_name->name;
570
    }
571
    pcgn->glyph = glyph;
572
    pcgn->str = str;
573
    return 0;
574
}
575
 
576
/*
577
 * Find the .notdef glyph in a font.
578
 */
579
private gs_glyph
580
find_notdef(gs_font_base *font)
581
{
582
    int index = 0;
583
    gs_glyph glyph;
584
 
585
    while (font->procs.enumerate_glyph((gs_font *)font, &index,
586
				       GLYPH_SPACE_NAME, &glyph),
587
	   index != 0)
588
	if (gs_font_glyph_is_notdef(font, glyph))
589
	    return glyph;
590
    return GS_NO_GLYPH;		/* best we can do */
591
}
592
 
593
/*
594
 * Add an Encoding entry to a character-indexed font (Type 1/2/42).
595
 */
596
private int
597
copied_char_add_encoding(gs_font *copied, gs_char chr, gs_glyph glyph)
598
{
599
    gs_copied_font_data_t *const cfdata = cf_data(copied);
600
    gs_glyph *Encoding = cfdata->Encoding;
601
    gs_copied_glyph_t *pslot;
602
    int code;
603
 
604
    if (Encoding == 0)
605
	return_error(gs_error_invalidaccess);
606
    if (chr >= 256 || glyph >= GS_MIN_CID_GLYPH)
607
	return_error(gs_error_rangecheck);
608
    code = copied_glyph_slot(cfdata, glyph, &pslot);
609
    if (code < 0)
610
	return code;
611
    if (Encoding[chr] != glyph && Encoding[chr] != GS_NO_GLYPH)
612
	return_error(gs_error_invalidaccess);
613
    Encoding[chr] = glyph;
614
    return 0;
615
}
616
 
617
/* Don't allow adding an Encoding entry. */
618
private int
619
copied_no_add_encoding(gs_font *copied, gs_char chr, gs_glyph glyph)
620
{
621
    return_error(gs_error_invalidaccess);
622
}
623
 
624
/* ---------------- Font procedures ---------------- */
625
 
626
private int
627
copied_font_info(gs_font *font, const gs_point *pscale, int members,
628
		 gs_font_info_t *info)
629
{
630
    if (pscale != 0)
631
	return_error(gs_error_rangecheck);
632
    *info = cf_data(font)->info;
633
    return 0;
634
}
635
 
636
private gs_glyph
637
copied_encode_char(gs_font *copied, gs_char chr, gs_glyph_space_t glyph_space)
638
{
639
    gs_copied_font_data_t *const cfdata = cf_data(copied);
640
    const gs_glyph *Encoding = cfdata->Encoding;
641
 
642
    if (chr >= 256 || Encoding == 0)
643
	return GS_NO_GLYPH;
644
    return Encoding[chr];
645
}
646
 
647
private int
648
copied_enumerate_glyph(gs_font *font, int *pindex,
649
		       gs_glyph_space_t glyph_space, gs_glyph *pglyph)
650
{
651
    gs_copied_font_data_t *const cfdata = cf_data(font);
652
 
653
    for (; *pindex < cfdata->glyphs_size; ++*pindex)
654
	if (cfdata->glyphs[*pindex].used) {
655
	    *pglyph =
656
		(glyph_space == GLYPH_SPACE_NAME && cfdata->names != 0 ?
657
		 cfdata->names[*pindex].glyph :
658
		 /* CIDFontType 0 uses CIDS as slot indices; CIDFontType 2 uses GIDs. */
659
		 *pindex + (glyph_space == GLYPH_SPACE_NAME 
660
			    ? GS_MIN_CID_GLYPH : GS_MIN_GLYPH_INDEX));
661
	    ++(*pindex);
662
	    return 0;
663
	}
664
    *pindex = 0;
665
    return 0;
666
}
667
 
668
private int
669
copied_glyph_name(gs_font *font, gs_glyph glyph, gs_const_string *pstr)
670
{
671
    gs_copied_font_data_t *const cfdata = cf_data(font);
672
    gs_copied_glyph_t *pcg;
673
 
674
    if (glyph >= GS_MIN_CID_GLYPH)
675
	return_error(gs_error_rangecheck);
676
    if (copied_glyph_slot(cfdata, glyph, &pcg) < 0)
677
	return_error(gs_error_undefined);
678
    *pstr = cfdata->names[pcg - cfdata->glyphs].str;
679
    return 0;
680
}
681
 
682
private int
683
copied_build_char(gs_text_enum_t *pte, gs_state *pgs, gs_font *font,
684
		  gs_char chr, gs_glyph glyph)
685
{
686
    int wmode = font->WMode;
687
    int code;
688
    gs_glyph_info_t info;
689
    double wxy[6];
690
    double sbw_stub[4]; /* Currently glyph_outline retrieves sbw only with type 1,2,9 fonts. */
691
 
692
    if (glyph == GS_NO_GLYPH) {
693
	glyph = font->procs.encode_char(font, chr, GLYPH_SPACE_INDEX);
694
	if (glyph == GS_NO_GLYPH) {
695
	    glyph = cf_data(font)->notdef;
696
	}
697
    }
698
    /*
699
     * Type 1/2 outlines don't require a current point, but TrueType
700
     * outlines do.  We might want to fix this someday....
701
     */
702
    if ((code = gs_moveto(pgs, 0.0, 0.0)) < 0 ||
703
	(code = font->procs.glyph_info(font, glyph, NULL,
704
				       (GLYPH_INFO_WIDTH << wmode) |
705
				       GLYPH_INFO_BBOX |
706
				       GLYPH_INFO_OUTLINE_WIDTHS,
707
				       &info)) < 0
708
	)
709
	return code;
710
    wxy[0] = info.width[wmode].x;
711
    wxy[1] = info.width[wmode].y;
712
    wxy[2] = info.bbox.p.x;
713
    wxy[3] = info.bbox.p.y;
714
    wxy[4] = info.bbox.q.x;
715
    wxy[5] = info.bbox.q.y;
716
    if ((code = gs_text_setcachedevice(pte, wxy)) < 0 ||
717
	(code = font->procs.glyph_outline(font, wmode, glyph, &ctm_only(pgs),
718
					  pgs->path, sbw_stub)) < 0
719
	)
720
	return code;
721
    if (font->PaintType != 0) {
722
	gs_setlinewidth(pgs, font->StrokeWidth);
723
	return gs_stroke(pgs);
724
    } else {
725
	return gs_fill(pgs);
726
    }
727
}
728
 
729
private inline bool 
730
compare_arrays(const float *v0, int l0, const float *v1, int l1)
731
{
732
    if (l0 != l1)
733
	return false;
734
    if (memcmp(v0, v1, l0 * sizeof(v0[0])))
735
	return false;
736
    return true;	
737
}
738
 
739
#define compare_tables(a, b) compare_arrays(a.values, a.count, b.values, b.count)
740
 
741
private int
742
compare_glyphs(const gs_font *cfont, const gs_font *ofont, gs_glyph *glyphs, 
743
			   int num_glyphs, int glyphs_step, int level)
744
{
745
    /* 
746
     * Checking widths because we can synthesize fonts from random fonts 
747
     * having same FontName and FontType. 
748
     * We must request width explicitely because Type 42 stores widths 
749
     * separately from outline data. We could skip it for Type 1, which doesn't.
750
     * We don't care of Metrics, Metrics2 because copied font never has them.
751
     */
752
    int i, WMode = ofont->WMode;
753
    int members = (GLYPH_INFO_WIDTH0 << WMode) | GLYPH_INFO_OUTLINE_WIDTHS | GLYPH_INFO_NUM_PIECES;
754
    gs_matrix mat;
755
    gs_copied_font_data_t *const cfdata = cf_data(cfont);
756
    int num_new_glyphs = 0;
757
 
758
    gs_make_identity(&mat);
759
    for (i = 0; i < num_glyphs; i++) {
760
	gs_glyph glyph = *(gs_glyph *)((byte *)glyphs + i * glyphs_step);
761
	gs_glyph pieces0[40], *pieces = pieces0;
762
	gs_glyph_info_t info0, info1;
763
	int code0 = ofont->procs.glyph_info((gs_font *)ofont, glyph, &mat, members, &info0);
764
	int code1 = cfont->procs.glyph_info((gs_font *)cfont, glyph, &mat, members, &info1);
765
	int code2, code;
766
 
767
	if (code0 == gs_error_undefined)
768
	    continue;
769
	if (code1 == gs_error_undefined) {
770
	    num_new_glyphs++;
771
	    if (num_new_glyphs > cfdata->glyphs_size - cfdata->num_glyphs)
772
		return 0;
773
	    continue;
774
	}
775
	if (code0 < 0)
776
	    return code0;
777
	if (code1 < 0)
778
	    return code1;
779
	if (info0.num_pieces != info1.num_pieces)
780
	    return 0;
781
	if (info0.width[WMode].x != info1.width[WMode].x ||
782
	    info0.width[WMode].y != info1.width[WMode].y)
783
	    return 0;
784
	if (WMode && (info0.v.x != info1.v.x || info0.v.y != info1.v.y))
785
	    return 0;
786
	if (info0.num_pieces > 0) {
787
	    if(level > 5)
788
		return_error(gs_error_rangecheck); /* abnormal glyph recursion */
789
	    if (info0.num_pieces > countof(pieces0) / 2) {
790
		pieces = (gs_glyph *)gs_alloc_bytes(cfont->memory, 
791
		    sizeof(glyphs) * info0.num_pieces * 2, "compare_glyphs");
792
		if (pieces == 0)
793
		    return_error(gs_error_VMerror);
794
	    }
795
	    info0.pieces = pieces;
796
	    info1.pieces = pieces + info0.num_pieces;
797
	    code0 = ofont->procs.glyph_info((gs_font *)ofont, glyph, &mat, 
798
				    GLYPH_INFO_PIECES, &info0);
799
	    code1 = cfont->procs.glyph_info((gs_font *)cfont, glyph, &mat, 
800
				    GLYPH_INFO_PIECES, &info1);
801
	    if (code0 >= 0 && code1 >= 0) {
802
		code2 = memcmp(info0.pieces, info1.pieces, info0.num_pieces * sizeof(*pieces));
803
		if (!code2)
804
		    code = compare_glyphs(cfont, ofont, pieces, info0.num_pieces, glyphs_step, level + 1);
805
		else
806
		    code = 0; /* Quiet compiler. */
807
	    } else
808
		code2 = code = 0;
809
	    if (pieces != pieces0)
810
		gs_free_object(cfont->memory, pieces, "compare_glyphs");
811
	    if (code0 == gs_error_undefined)
812
		continue;
813
	    if (code1 == gs_error_undefined) {
814
		num_new_glyphs++;
815
		if (num_new_glyphs > cfdata->glyphs_size - cfdata->num_glyphs)
816
		    return 0;
817
		continue;
818
	    }
819
	    if (code0 < 0)
820
		return code0;
821
	    if (code1 < 0)
822
		return code1;
823
	    if (code2 || code == 0) {
824
		return 0;
825
	    }
826
	} else {
827
	    gs_glyph_data_t gdata0, gdata1;
828
 
829
	    switch(cfont->FontType) {
830
		case ft_encrypted:
831
		case ft_encrypted2: {
832
		    gs_font_type1 *font0 = (gs_font_type1 *)cfont;
833
		    gs_font_type1 *font1 = (gs_font_type1 *)ofont;
834
 
835
		    gdata0.memory = font0->memory;
836
		    gdata1.memory = font1->memory;
837
		    code0 = font0->data.procs.glyph_data(font0, glyph, &gdata0);
838
		    code1 = font1->data.procs.glyph_data(font1, glyph, &gdata1);
839
		    break;
840
		}
841
		case ft_TrueType: 
842
		case ft_CID_TrueType: {
843
		    gs_font_type42 *font0 = (gs_font_type42 *)cfont;
844
		    gs_font_type42 *font1 = (gs_font_type42 *)ofont;
845
		    uint glyph_index0 = font0->data.get_glyph_index(font0, glyph);
846
		    uint glyph_index1 = font1->data.get_glyph_index(font1, glyph);
847
 
848
		    gdata0.memory = font0->memory;
849
		    gdata1.memory = font1->memory;
850
		    code0 = font0->data.get_outline(font0, glyph_index0, &gdata0);
851
		    code1 = font1->data.get_outline(font1, glyph_index1, &gdata1);
852
		    break;
853
		}
854
		case ft_CID_encrypted: {
855
		    gs_font_cid0 *font0 = (gs_font_cid0 *)cfont;
856
		    gs_font_cid0 *font1 = (gs_font_cid0 *)ofont;
857
		    int fidx0, fidx1;
858
 
859
		    gdata0.memory = font0->memory;
860
		    gdata1.memory = font1->memory;
861
		    code0 = font0->cidata.glyph_data((gs_font_base *)font0, glyph, &gdata0, &fidx0);
862
		    code1 = font1->cidata.glyph_data((gs_font_base *)font1, glyph, &gdata1, &fidx1);
863
		    break;
864
		}
865
		default:
866
		    return_error(gs_error_unregistered); /* unimplemented */
867
	    }
868
	    if (code0 < 0) {
869
		if (code1 >= 0)
870
		    gs_glyph_data_free(&gdata1, "compare_glyphs");
871
		return code0;
872
	    }
873
	    if (code1 < 0) {
874
		if (code0 >= 0)
875
		    gs_glyph_data_free(&gdata0, "compare_glyphs");
876
		return code1;
877
	    }
878
	    if (gdata0.bits.size != gdata1.bits.size)
879
		return 0;
880
	    if (memcmp(gdata0.bits.data, gdata0.bits.data, gdata0.bits.size))
881
		return 0;
882
	    gs_glyph_data_free(&gdata0, "compare_glyphs");
883
	    gs_glyph_data_free(&gdata1, "compare_glyphs");
884
	}
885
    }
886
    return 1;
887
}
888
 
889
/* ---------------- Individual FontTypes ---------------- */
890
 
891
/* ------ Type 1 ------ */
892
 
893
private int
894
copied_type1_glyph_data(gs_font_type1 * pfont, gs_glyph glyph,
895
			gs_glyph_data_t *pgd)
896
{
897
    gs_copied_font_data_t *const cfdata = cf_data((gs_font *)pfont);
898
    gs_copied_glyph_t *pslot;
899
    int code = copied_glyph_slot(cfdata, glyph, &pslot);
900
 
901
    if (code < 0)
902
	return code;
903
    gs_glyph_data_from_string(pgd, pslot->gdata.data, pslot->gdata.size,
904
			      NULL);
905
    return 0;
906
}
907
 
908
private int
909
copied_type1_subr_data(gs_font_type1 * pfont, int subr_num, bool global,
910
		       gs_glyph_data_t *pgd)
911
{
912
    gs_copied_font_data_t *const cfdata = cf_data((gs_font *)pfont);
913
    const gs_subr_info_t *psi =
914
	(global ? &cfdata->global_subrs : &cfdata->subrs);
915
 
916
    if (subr_num < 0 || subr_num >= psi->count)
917
	return_error(gs_error_rangecheck);
918
    gs_glyph_data_from_string(pgd, psi->data + psi->starts[subr_num],
919
			      psi->starts[subr_num + 1] -
920
			        psi->starts[subr_num],
921
			      NULL);
922
    return 0;
923
}
924
 
925
private int
926
copied_type1_seac_data(gs_font_type1 * pfont, int ccode,
927
		       gs_glyph * pglyph, gs_const_string *gstr, gs_glyph_data_t *pgd)
928
{
929
    /*
930
     * This can only be invoked if the components have already been
931
     * copied to their proper positions, so it is simple.
932
     */
933
    gs_glyph glyph = gs_c_known_encode((gs_char)ccode, ENCODING_INDEX_STANDARD);
934
    gs_glyph glyph1;
935
    int code;
936
 
937
    if (glyph == GS_NO_GLYPH)
938
	return_error(gs_error_rangecheck);
939
    code = gs_c_glyph_name(glyph, gstr);
940
    if (code < 0)
941
	return code;
942
    code = pfont->dir->global_glyph_code(pfont->memory, gstr, &glyph1);
943
    if (code < 0)
944
	return code;
945
    if (pglyph)
946
	*pglyph = glyph1;
947
    if (pgd)
948
	return copied_type1_glyph_data(pfont, glyph1, pgd);
949
    else
950
	return 0;
951
}
952
 
953
private int
954
copied_type1_push_values(void *callback_data, const fixed *values, int count)
955
{
956
    return_error(gs_error_unregistered);
957
}
958
 
959
private int
960
copied_type1_pop_value(void *callback_data, fixed *value)
961
{
962
    return_error(gs_error_unregistered);
963
}
964
 
965
private int
966
copy_font_type1(gs_font *font, gs_font *copied)
967
{
968
    gs_font_type1 *font1 = (gs_font_type1 *)font;
969
    gs_font_type1 *copied1 = (gs_font_type1 *)copied;
970
    gs_copied_font_data_t *const cfdata = cf_data(copied);
971
    int code;
972
 
973
    cfdata->notdef = find_notdef((gs_font_base *)font);
974
    code = copied_Encoding_alloc(copied);
975
    if (code < 0)
976
	return code;
977
    if ((code = copy_subrs(font1, false, &cfdata->subrs, copied->memory)) < 0 ||
978
	(code = copy_subrs(font1, true, &cfdata->global_subrs, copied->memory)) < 0
979
	) {
980
	gs_free_object(copied->memory, cfdata->Encoding,
981
		       "copy_font_type1(Encoding)");
982
	return code;
983
    }
984
    /*
985
     * We don't need real push/pop procedures, because we can't do anything
986
     * useful with fonts that have non-standard OtherSubrs anyway.
987
     */
988
    copied1->data.procs.glyph_data = copied_type1_glyph_data;
989
    copied1->data.procs.subr_data = copied_type1_subr_data;
990
    copied1->data.procs.seac_data = copied_type1_seac_data;
991
    copied1->data.procs.push_values = copied_type1_push_values;
992
    copied1->data.procs.pop_value = copied_type1_pop_value;
993
    copied1->data.proc_data = 0;
994
    return 0;
995
}
996
 
997
private int
998
copy_glyph_type1(gs_font *font, gs_glyph glyph, gs_font *copied, int options)
999
{
1000
    gs_glyph_data_t gdata;
1001
    gs_font_type1 *font1 = (gs_font_type1 *)font;
1002
    int code;
1003
    int rcode;
1004
 
1005
    gdata.memory = font->memory;
1006
    code = font1->data.procs.glyph_data(font1, glyph, &gdata);
1007
    if (code < 0)
1008
	return code;
1009
    code = copy_glyph_data(font, glyph, copied, options, &gdata, NULL, 0);
1010
    if (code < 0)
1011
	return code;
1012
    rcode = code;
1013
    if (code == 0)
1014
	code = copy_glyph_name(font, glyph, copied, glyph);
1015
    return (code < 0 ? code : rcode);
1016
}
1017
 
1018
private int
1019
copied_type1_glyph_outline(gs_font *font, int WMode, gs_glyph glyph,
1020
			   const gs_matrix *pmat, gx_path *ppath, double sbw[4])
1021
{   /* 
1022
     * 'WMode' may be inherited from an upper font.
1023
     * We ignore in because Type 1,2 charstrings do not depend on it.
1024
     */
1025
 
1026
    /*
1027
     * This code duplicates much of zcharstring_outline in zchar1.c.
1028
     * This is unfortunate, but we don't see a simple way to refactor the
1029
     * code to avoid it.
1030
     */
1031
    gs_glyph_data_t gdata;
1032
    gs_font_type1 *const pfont1 = (gs_font_type1 *)font;
1033
    int code;
1034
    const gs_glyph_data_t *pgd = &gdata;
1035
    gs_type1_state cis;
1036
    gs_imager_state gis;
1037
 
1038
    gdata.memory = pfont1->memory;
1039
    code = pfont1->data.procs.glyph_data(pfont1, glyph, &gdata);
1040
    if (code < 0)
1041
	return code;
1042
    if (pgd->bits.size <= max(pfont1->data.lenIV, 0))
1043
	return_error(gs_error_invalidfont);
1044
    /* Initialize just enough of the imager state. */
1045
    if (pmat)
1046
	gs_matrix_fixed_from_matrix(&gis.ctm, pmat);
1047
    else {
1048
	gs_matrix imat;
1049
 
1050
	gs_make_identity(&imat);
1051
	gs_matrix_fixed_from_matrix(&gis.ctm, &imat);
1052
    }
1053
    gis.flatness = 0;
1054
    code = gs_type1_interp_init(&cis, &gis, ppath, NULL, NULL, true, 0,
1055
				pfont1);
1056
    if (code < 0)
1057
	return code;
1058
    cis.no_grid_fitting = true;
1059
    /* Continue interpreting. */
1060
    for (;;) {
1061
	int value;
1062
 
1063
	code = pfont1->data.interpret(&cis, pgd, &value);
1064
	switch (code) {
1065
	case 0:		/* all done */
1066
	    /* falls through */
1067
	default:		/* code < 0, error */
1068
	    return code;
1069
	case type1_result_callothersubr:	/* unknown OtherSubr */
1070
	    return_error(gs_error_rangecheck); /* can't handle it */
1071
	case type1_result_sbw:	/* [h]sbw, just continue */
1072
	    pgd = 0;
1073
    	    type1_cis_get_metrics(&cis, sbw);
1074
	}
1075
    }
1076
}
1077
 
1078
private const gs_copied_font_procs_t copied_procs_type1 = {
1079
    copy_font_type1, copy_glyph_type1, copied_char_add_encoding,
1080
    named_glyph_slot_hashed,
1081
    copied_encode_char, gs_type1_glyph_info, copied_type1_glyph_outline
1082
};
1083
 
1084
private bool 
1085
same_type1_subrs(const gs_font_type1 *cfont, const gs_font_type1 *ofont, 
1086
		 bool global)
1087
{
1088
    gs_glyph_data_t gdata0, gdata1;
1089
    int i, code = 0;
1090
    bool exit = false;
1091
 
1092
    gdata0.memory = cfont->memory;
1093
    gdata1.memory = ofont->memory;
1094
    /* Scan the font to determine the size of the subrs. */
1095
    for (i = 0; !exit; i++) {
1096
	int code0 = cfont->data.procs.subr_data((gs_font_type1 *)cfont, 
1097
						i, global, &gdata0);
1098
	int code1 = ofont->data.procs.subr_data((gs_font_type1 *)ofont, 
1099
						i, global, &gdata1);
1100
	bool missing0, missing1;
1101
 
1102
	if (code0 == gs_error_rangecheck && code1 == gs_error_rangecheck)
1103
	    return 1; /* Both arrays exceeded. */
1104
	/*  Some fonts use null for skiping elements in subrs array. 
1105
	    This gives typecheck.
1106
	*/
1107
	missing0 = (code0 == gs_error_rangecheck || code0 == gs_error_typecheck);
1108
	missing1 = (code1 == gs_error_rangecheck || code1 == gs_error_typecheck);
1109
	if (missing0 && missing1)
1110
	    continue;
1111
	if (missing0 && !missing1)
1112
	    return 0; /* The copy has insufficient subrs. */
1113
	if (missing1)
1114
	    continue;
1115
	if (code0 < 0)
1116
	    code = code0, exit = true;
1117
	else if (code1 < 0)
1118
	    code = code1, exit = true;
1119
	else if (gdata0.bits.size != gdata1.bits.size)
1120
	    exit = true;
1121
	else if (memcmp(gdata0.bits.data, gdata1.bits.data, gdata0.bits.size))
1122
	    exit = true;
1123
	if (code0 > 0)
1124
	    gs_glyph_data_free(&gdata0, "same_type1_subrs");
1125
	if (code1 > 0)
1126
	    gs_glyph_data_free(&gdata1, "same_type1_subrs");
1127
    }
1128
    return code;
1129
}
1130
 
1131
private bool 
1132
same_type1_hinting(const gs_font_type1 *cfont, const gs_font_type1 *ofont)
1133
{
1134
    const gs_type1_data *d0 = &cfont->data, *d1 = &ofont->data;
1135
 
1136
    if (d0->lenIV != d1->lenIV)
1137
	return false;
1138
    /*
1139
    if (d0->defaultWidthX != d1->defaultWidthX)
1140
	return false;
1141
    if (d0->nominalWidthX != d1->nominalWidthX)
1142
	return false;
1143
    */
1144
    if (d0->BlueFuzz != d1->BlueFuzz)
1145
	return false;
1146
    if (d0->BlueScale != d1->BlueScale)
1147
	return false;
1148
    if (d0->BlueShift != d1->BlueShift)
1149
	return false;
1150
    if (d0->ExpansionFactor != d1->ExpansionFactor)
1151
	return false;
1152
    if (d0->ForceBold != d1->ForceBold)
1153
	return false;
1154
    if (!compare_tables(d0->FamilyBlues, d1->FamilyBlues))
1155
	return false;
1156
    if (!compare_tables(d0->FamilyOtherBlues, d1->FamilyOtherBlues))
1157
	return false;
1158
    if (d0->LanguageGroup != d1->LanguageGroup)
1159
	return false;
1160
    if (!compare_tables(d0->OtherBlues, d1->OtherBlues))
1161
	return false;
1162
    if (d0->RndStemUp != d1->RndStemUp)
1163
	return false;
1164
    if (!compare_tables(d0->StdHW, d1->StdHW))
1165
	return false;
1166
    if (!compare_tables(d0->StemSnapH, d1->StemSnapH))
1167
	return false;
1168
    if (!compare_tables(d0->StemSnapV, d1->StemSnapV))
1169
	return false;
1170
    if (!compare_tables(d0->WeightVector, d1->WeightVector))
1171
	return false;
1172
    if (!same_type1_subrs(cfont, ofont, false))
1173
	return false;
1174
    if (!same_type1_subrs(cfont, ofont, true))
1175
	return false;
1176
    /*
1177
     *	We ignore differences in OtherSubrs because pdfwrite
1178
     *	must build without PS interpreter and therefore copied font
1179
     *	have no storage for them.
1180
     */
1181
    return true;
1182
}
1183
 
1184
/* ------ Type 42 ------ */
1185
 
1186
private int
1187
copied_type42_string_proc(gs_font_type42 *font, ulong offset, uint len,
1188
			  const byte **pstr)
1189
{
1190
    gs_copied_font_data_t *const cfdata = font->data.proc_data;
1191
 
1192
    if (offset + len > cfdata->data_size)
1193
	return_error(gs_error_rangecheck);
1194
    *pstr = cfdata->data + offset;
1195
    return 0;
1196
}
1197
 
1198
private int
1199
copied_type42_get_outline(gs_font_type42 *font, uint glyph_index,
1200
			  gs_glyph_data_t *pgd)
1201
{
1202
    gs_copied_font_data_t *const cfdata = font->data.proc_data;
1203
    gs_copied_glyph_t *pcg;
1204
 
1205
    if (glyph_index >= cfdata->glyphs_size)
1206
	return_error(gs_error_rangecheck);
1207
    pcg = &cfdata->glyphs[glyph_index];
1208
    if (!pcg->used)
1209
	gs_glyph_data_from_null(pgd);
1210
    else
1211
	gs_glyph_data_from_string(pgd, pcg->gdata.data, pcg->gdata.size, NULL);
1212
    return 0;
1213
}
1214
 
1215
private int
1216
copied_type42_get_metrics(gs_font_type42 * pfont, uint glyph_index,
1217
			  int wmode, float sbw[4])
1218
{
1219
    /* Check whether we have metrics for this (glyph,wmode) pair. */
1220
    gs_copied_font_data_t *const cfdata = pfont->data.proc_data;
1221
    gs_copied_glyph_t *pcg;
1222
 
1223
    if (glyph_index >= cfdata->glyphs_size)
1224
	return_error(gs_error_rangecheck);
1225
    pcg = &cfdata->glyphs[glyph_index];
1226
    if (!(pcg->used & (HAS_SBW0 << wmode)))
1227
	return_error(gs_error_undefined);
1228
    return gs_type42_default_get_metrics(pfont, glyph_index, wmode, sbw);
1229
}
1230
 
1231
private uint
1232
copied_type42_get_glyph_index(gs_font_type42 *font, gs_glyph glyph)
1233
{
1234
    gs_copied_font_data_t *const cfdata = cf_data((gs_font *)font);
1235
    gs_copied_glyph_t *pcg;
1236
    int code = copied_glyph_slot(cfdata, glyph, &pcg);
1237
 
1238
    if (code < 0)
1239
	return GS_NO_GLYPH;
1240
    return pcg - cfdata->glyphs;
1241
}
1242
 
1243
private int
1244
copy_font_type42(gs_font *font, gs_font *copied)
1245
{
1246
    gs_font_type42 *const font42 = (gs_font_type42 *)font;
1247
    gs_font_type42 *const copied42 = (gs_font_type42 *)copied;
1248
    gs_copied_font_data_t *const cfdata = cf_data(copied);
1249
    /*
1250
     * We "write" the font, aside from the glyphs, into an in-memory
1251
     * structure, and access it from there.
1252
     * We allocate room at the end of the copied data for fake hmtx/vmtx.
1253
     */
1254
    uint extra = font42->data.trueNumGlyphs * 8;
1255
    stream fs;
1256
    int code;
1257
 
1258
    cfdata->notdef = find_notdef((gs_font_base *)font);
1259
    code = copied_Encoding_alloc(copied);
1260
    if (code < 0)
1261
	return code;
1262
    s_init(&fs, font->memory);
1263
    swrite_position_only(&fs);
1264
    code = (font->FontType == ft_TrueType ? psf_write_truetype_stripped(&fs, font42)
1265
					  : psf_write_cid2_stripped(&fs, (gs_font_cid2 *)font42));
1266
    code = copied_data_alloc(copied, &fs, extra, code);
1267
    if (code < 0)
1268
	goto fail;
1269
    if (font->FontType == ft_TrueType)
1270
	psf_write_truetype_stripped(&fs, font42);
1271
    else
1272
	psf_write_cid2_stripped(&fs, (gs_font_cid2 *)font42);
1273
    copied42->data.string_proc = copied_type42_string_proc;
1274
    copied42->data.proc_data = cfdata;
1275
    code = gs_type42_font_init(copied42);
1276
    if (code < 0)
1277
	goto fail2;
1278
    /* gs_type42_font_init overwrites enumerate_glyph. */
1279
    copied42->procs.enumerate_glyph = copied_enumerate_glyph;
1280
    copied42->data.get_glyph_index = copied_type42_get_glyph_index;
1281
    copied42->data.get_outline = copied_type42_get_outline;
1282
    copied42->data.get_metrics = copied_type42_get_metrics;
1283
    copied42->data.metrics[0].numMetrics =
1284
	copied42->data.metrics[1].numMetrics =
1285
	extra / 8;
1286
    copied42->data.metrics[0].offset = cfdata->data_size - extra;
1287
    copied42->data.metrics[1].offset = cfdata->data_size - extra / 2;
1288
    copied42->data.metrics[0].length =
1289
	copied42->data.metrics[1].length =
1290
	extra / 2;
1291
    memset(cfdata->data + cfdata->data_size - extra, 0, extra);
1292
    copied42->data.numGlyphs = font42->data.numGlyphs;
1293
    copied42->data.trueNumGlyphs = font42->data.trueNumGlyphs;
1294
    return 0;
1295
 fail2:
1296
    gs_free_object(copied->memory, cfdata->data,
1297
		   "copy_font_type42(data)");
1298
 fail:
1299
    gs_free_object(copied->memory, cfdata->Encoding,
1300
		   "copy_font_type42(Encoding)");
1301
    return code;
1302
}
1303
 
1304
private int
1305
copy_glyph_type42(gs_font *font, gs_glyph glyph, gs_font *copied, int options)
1306
{
1307
    gs_glyph_data_t gdata;
1308
    gs_font_type42 *font42 = (gs_font_type42 *)font;
1309
    gs_font_cid2 *fontCID2 = (gs_font_cid2 *)font;
1310
    gs_font_type42 *const copied42 = (gs_font_type42 *)copied;
1311
    uint gid = (options & COPY_GLYPH_BY_INDEX ? glyph - GS_MIN_GLYPH_INDEX :
1312
		font->FontType == ft_CID_TrueType 
1313
		    ? fontCID2->cidata.CIDMap_proc(fontCID2, glyph)
1314
		    : font42->data.get_glyph_index(font42, glyph));
1315
    int code;
1316
    int rcode;
1317
    gs_copied_font_data_t *const cfdata = cf_data(copied);
1318
    gs_copied_glyph_t *pcg;
1319
    float sbw[4];
1320
    double factor = font42->data.unitsPerEm;
1321
    int i;
1322
 
1323
    gdata.memory = font42->memory;
1324
    code = font42->data.get_outline(font42, gid, &gdata);
1325
    if (code < 0)
1326
	return code;
1327
    code = copy_glyph_data(font, gid + GS_MIN_GLYPH_INDEX, copied, options,
1328
			   &gdata, NULL, 0);
1329
    if (code < 0)
1330
	return code;
1331
    rcode = code;
1332
    if (glyph < GS_MIN_CID_GLYPH)
1333
	code = copy_glyph_name(font, glyph, copied,
1334
			       gid + GS_MIN_GLYPH_INDEX);
1335
    DISCARD(copied_glyph_slot(cfdata, gid + GS_MIN_GLYPH_INDEX, &pcg)); /* can't fail */
1336
    for (i = 0; i < 2; ++i) {
1337
	if (font42->data.get_metrics(font42, gid, i, sbw) >= 0) {
1338
	    int sb = (int)(sbw[i] * factor + 0.5);
1339
	    uint width = (uint)(sbw[2 + i] * factor + 0.5);
1340
	    byte *pmetrics =
1341
		cfdata->data + copied42->data.metrics[i].offset + gid * 4;
1342
 
1343
	    pmetrics[0] = (byte)(width >> 8);
1344
	    pmetrics[1] = (byte)width;
1345
	    pmetrics[2] = (byte)(sb >> 8);
1346
	    pmetrics[3] = (byte)sb;
1347
	    pcg->used |= HAS_SBW0 << i;
1348
	}
1349
	factor = -factor;	/* values are negated for WMode = 1 */
1350
    }
1351
    return (code < 0 ? code : rcode);
1352
}
1353
 
1354
private gs_glyph
1355
copied_type42_encode_char(gs_font *copied, gs_char chr,
1356
			  gs_glyph_space_t glyph_space)
1357
{
1358
    gs_copied_font_data_t *const cfdata = cf_data(copied);
1359
    const gs_glyph *Encoding = cfdata->Encoding;
1360
    gs_glyph glyph;
1361
 
1362
    if (chr >= 256 || Encoding == 0)
1363
	return GS_NO_GLYPH;
1364
    glyph = Encoding[chr];
1365
    if (glyph_space == GLYPH_SPACE_INDEX) {
1366
	/* Search linearly for the glyph by name. */
1367
	gs_copied_glyph_t *pcg;
1368
	int code = named_glyph_slot_linear(cfdata, glyph, &pcg);
1369
 
1370
	if (code < 0 || !pcg->used)
1371
	    return GS_NO_GLYPH;
1372
	return GS_MIN_GLYPH_INDEX + (pcg - cfdata->glyphs);
1373
    }
1374
    return glyph;
1375
}
1376
 
1377
 
1378
private const gs_copied_font_procs_t copied_procs_type42 = {
1379
    copy_font_type42, copy_glyph_type42, copied_char_add_encoding,
1380
    named_glyph_slot_linear,
1381
    copied_type42_encode_char, gs_type42_glyph_info, gs_type42_glyph_outline
1382
};
1383
 
1384
private inline int
1385
access_type42_data(gs_font_type42 *pfont, ulong base, ulong length, 
1386
		   const byte **vptr)
1387
{
1388
    /* See ACCESS macro in gstype42.c */
1389
    return pfont->data.string_proc(pfont, base, length, vptr);
1390
}
1391
 
1392
private inline uint
1393
U16(const byte *p)
1394
{
1395
    return ((uint)p[0] << 8) + p[1];
1396
}
1397
 
1398
private int
1399
same_type42_hinting(gs_font_type42 *font0, gs_font_type42 *font1)
1400
{
1401
    gs_type42_data *d0 = &font0->data, *d1 = &font1->data;
1402
    gs_font_type42 *font[2];
1403
    uint pos[2][3];
1404
    uint len[2][3] = {{0,0,0}, {0,0,0}};
1405
    int i, j, code;
1406
 
1407
    if (d0->unitsPerEm != d1->unitsPerEm)
1408
	return 0;
1409
    font[0] = font0;
1410
    font[1] = font1;
1411
    memset(pos, 0, sizeof(pos));
1412
    for (j = 0; j < 2; j++) {
1413
	const byte *OffsetTable;
1414
	uint numTables;
1415
 
1416
	code = access_type42_data(font[j], 0, 12, &OffsetTable);
1417
	if (code < 0)
1418
	    return code;
1419
	numTables = U16(OffsetTable + 4);
1420
	for (i = 0; i < numTables; ++i) {
1421
	    const byte *tab;
1422
	    ulong start;
1423
	    uint length;
1424
 
1425
	    code = access_type42_data(font[j], 12 + i * 16, 16, &tab);
1426
	    if (code < 0)
1427
		return code;
1428
	    start = get_u32_msb(tab + 8);
1429
	    length = get_u32_msb(tab + 12);
1430
	    if (!memcmp("prep", tab, 4))
1431
		pos[j][0] = start, len[j][0] = length;
1432
	    else if (!memcmp("cvt ", tab, 4))
1433
		pos[j][1] = start, len[j][1] = length;
1434
	    else if (!memcmp("fpgm", tab, 4))
1435
		pos[j][2] = start, len[j][2] = length;
1436
	}
1437
    }
1438
    for (i = 0; i < 3; i++) {
1439
	if (len[0][i] != len[1][i])
1440
	    return 0;
1441
    }
1442
    for (i = 0; i < 3; i++) {
1443
	if (len[0][i] != 0) {
1444
	    const byte *data0, *data1;
1445
 
1446
	    code = access_type42_data(font0, pos[0][i], len[0][i], &data0);
1447
	    if (code < 0)
1448
		return code;
1449
	    code = access_type42_data(font1, pos[1][i], len[1][i], &data1);
1450
	    if (code < 0)
1451
		return code;
1452
	    if (memcmp(data0, data1, len[1][i]))
1453
		return 0;
1454
	}
1455
    }
1456
    return 1;
1457
}
1458
 
1459
#undef ACCESS
1460
 
1461
/* ------ CIDFont shared ------ */
1462
 
1463
private int
1464
copy_font_cid_common(gs_font *font, gs_font *copied, gs_font_cid_data *pcdata)
1465
{
1466
    return (copy_string(copied->memory, &pcdata->CIDSystemInfo.Registry,
1467
			"Registry") |
1468
	    copy_string(copied->memory, &pcdata->CIDSystemInfo.Ordering,
1469
			"Ordering"));
1470
}
1471
 
1472
/* ------ CIDFontType 0 ------ */
1473
 
1474
private int
1475
copied_cid0_glyph_data(gs_font_base *font, gs_glyph glyph,
1476
		       gs_glyph_data_t *pgd, int *pfidx)
1477
{
1478
    gs_font_cid0 *fcid0 = (gs_font_cid0 *)font;
1479
    gs_copied_font_data_t *const cfdata = cf_data((gs_font *)font);
1480
    gs_copied_glyph_t *pcg;
1481
    int code = copied_glyph_slot(cfdata, glyph, &pcg);
1482
    int fdbytes = fcid0->cidata.FDBytes;
1483
    int i;
1484
 
1485
    if (pfidx)
1486
	*pfidx = 0;
1487
    if (code < 0) {
1488
	if (pgd)
1489
	    gs_glyph_data_from_null(pgd);
1490
	return_error(gs_error_undefined);
1491
    }
1492
    if (pfidx)
1493
	for (i = 0; i < fdbytes; ++i)
1494
	    *pfidx = (*pfidx << 8) + pcg->gdata.data[i];
1495
    if (pgd)
1496
	gs_glyph_data_from_string(pgd, pcg->gdata.data + fdbytes,
1497
				  pcg->gdata.size - fdbytes, NULL);
1498
    return 0;
1499
}
1500
private int
1501
copied_sub_type1_glyph_data(gs_font_type1 * pfont, gs_glyph glyph,
1502
			    gs_glyph_data_t *pgd)
1503
{
1504
    return
1505
      copied_cid0_glyph_data((gs_font_base *)cf_data((gs_font *)pfont)->parent,
1506
			     glyph, pgd, NULL);
1507
}
1508
 
1509
private int
1510
cid0_subfont(gs_font *copied, gs_glyph glyph, gs_font_type1 **pfont1)
1511
{
1512
    int fidx;
1513
    int code = copied_cid0_glyph_data((gs_font_base *)copied, glyph, NULL,
1514
				      &fidx);
1515
 
1516
    if (code >= 0) {
1517
	gs_font_cid0 *font0 = (gs_font_cid0 *)copied;
1518
 
1519
	if (fidx >= font0->cidata.FDArray_size)
1520
	    return_error(gs_error_unregistered); /* Must not happen. */
1521
	*pfont1 = font0->cidata.FDArray[fidx];
1522
    }
1523
    return code;
1524
}
1525
 
1526
private int
1527
copied_cid0_glyph_info(gs_font *font, gs_glyph glyph, const gs_matrix *pmat,
1528
		       int members, gs_glyph_info_t *info)
1529
{
1530
    gs_font_type1 *subfont1;
1531
    int code = cid0_subfont(font, glyph, &subfont1);
1532
 
1533
    if (code < 0)
1534
	return code;
1535
    if (members & GLYPH_INFO_WIDTH1) {
1536
	/* Hack : There is no way to pass WMode from font to glyph_info,
1537
	 * and usually CID font has no metrics for WMode 1.
1538
	 * Therefore we use FontBBox as default size.
1539
	 * Warning : this incompletely implements the request :
1540
	 * other requested members are not retrieved.
1541
	 */ 
1542
	gs_font_info_t finfo;
1543
	int code = subfont1->procs.font_info(font, NULL, FONT_INFO_BBOX, &finfo);
1544
 
1545
	if (code < 0)
1546
	    return code;
1547
	info->width[1].x = 0;
1548
	info->width[1].y = -finfo.BBox.q.x; /* Sic! */
1549
	info->v.x = finfo.BBox.q.x / 2;
1550
	info->v.y = finfo.BBox.q.y;
1551
	info->members = GLYPH_INFO_WIDTH1;
1552
	return 0;
1553
    }
1554
    return subfont1->procs.glyph_info((gs_font *)subfont1, glyph, pmat,
1555
				      members, info);
1556
}
1557
 
1558
private int
1559
copied_cid0_glyph_outline(gs_font *font, int WMode, gs_glyph glyph,
1560
			  const gs_matrix *pmat, gx_path *ppath, double sbw[4])
1561
{
1562
    gs_font_type1 *subfont1;
1563
    int code = cid0_subfont(font, glyph, &subfont1);
1564
 
1565
    if (code < 0)
1566
	return code;
1567
    return subfont1->procs.glyph_outline((gs_font *)subfont1, WMode, glyph, pmat,
1568
					 ppath, sbw);
1569
}
1570
 
1571
private int
1572
copy_font_cid0(gs_font *font, gs_font *copied)
1573
{
1574
    gs_font_cid0 *copied0 = (gs_font_cid0 *)copied;
1575
    gs_copied_font_data_t *const cfdata = cf_data(copied);
1576
    gs_font_type1 **FDArray =
1577
	gs_alloc_struct_array(copied->memory, copied0->cidata.FDArray_size,
1578
			      gs_font_type1 *,
1579
			      &st_gs_font_type1_ptr_element, "FDArray");
1580
    int i = 0, code;
1581
 
1582
    if (FDArray == 0)
1583
	return_error(gs_error_VMerror);
1584
    code = copy_font_cid_common(font, copied, &copied0->cidata.common);
1585
    if (code < 0)
1586
	goto fail;
1587
    for (; i < copied0->cidata.FDArray_size; ++i) {
1588
	gs_font *subfont = (gs_font *)copied0->cidata.FDArray[i];
1589
	gs_font_type1 *subfont1 = (gs_font_type1 *)subfont;
1590
	gs_font *subcopy;
1591
	gs_font_type1 *subcopy1;
1592
	gs_copied_font_data_t *subdata;
1593
 
1594
	if (i == 0) {
1595
	    /* copy_subrs requires a Type 1 font, even for GSubrs. */
1596
	    code = copy_subrs(subfont1, true, &cfdata->global_subrs,
1597
			      copied->memory);
1598
	    if (code < 0)
1599
		goto fail;
1600
	}
1601
	code = gs_copy_font(subfont, &subfont->FontMatrix, copied->memory, &subcopy);
1602
	if (code < 0)
1603
	    goto fail;
1604
	subcopy1 = (gs_font_type1 *)subcopy;
1605
	subcopy1->data.parent = NULL;
1606
	subdata = cf_data(subcopy);
1607
	subdata->parent = copied0;
1608
	gs_free_object(copied->memory, subdata->Encoding,
1609
		       "copy_font_cid0(Encoding)");
1610
	subdata->Encoding = 0;
1611
	/*
1612
	 * Share the glyph data and global_subrs with the parent.  This
1613
	 * allows copied_type1_glyph_data in the subfont to do the right
1614
	 * thing.
1615
	 */
1616
	gs_free_object(copied->memory, subdata->names,
1617
		       "copy_font_cid0(subfont names)");
1618
	gs_free_object(copied->memory, subdata->glyphs,
1619
		       "copy_font_cid0(subfont glyphs)");
1620
	subcopy1->data.procs.glyph_data = copied_sub_type1_glyph_data;
1621
	subdata->glyphs = cfdata->glyphs;
1622
	subdata->glyphs_size = cfdata->glyphs_size;
1623
	subdata->names = 0;
1624
	subdata->global_subrs = cfdata->global_subrs;
1625
	FDArray[i] = subcopy1;
1626
    }
1627
    cfdata->notdef = GS_MIN_CID_GLYPH;
1628
    copied0->cidata.FDArray = FDArray;
1629
    copied0->cidata.FDBytes =
1630
	(copied0->cidata.FDArray_size <= 1 ? 0 :
1631
	 copied0->cidata.FDArray_size <= 256 ? 1 : 2);
1632
    copied0->cidata.glyph_data = copied_cid0_glyph_data;
1633
    return 0;
1634
 fail:
1635
    while (--i >= 0)
1636
	gs_free_object(copied->memory, FDArray[i], "copy_font_cid0(subfont)");
1637
    gs_free_object(copied->memory, FDArray, "FDArray");
1638
    return code;
1639
}
1640
 
1641
private int
1642
copy_glyph_cid0(gs_font *font, gs_glyph glyph, gs_font *copied, int options)
1643
{
1644
    gs_glyph_data_t gdata;
1645
    gs_font_cid0 *fcid0 = (gs_font_cid0 *)font;
1646
    gs_font_cid0 *copied0 = (gs_font_cid0 *)copied;
1647
    int fdbytes = copied0->cidata.FDBytes;
1648
    int fidx;
1649
    int code;
1650
    byte prefix[MAX_FDBytes];
1651
    int i;
1652
 
1653
    gdata.memory = font->memory;
1654
    code = fcid0->cidata.glyph_data((gs_font_base *)font, glyph,
1655
		&gdata, &fidx);
1656
    if (code < 0)
1657
	return code;
1658
    for (i = fdbytes - 1; i >= 0; --i, fidx >>= 8)
1659
	prefix[i] = (byte)fidx;
1660
    if (fidx != 0)
1661
	return_error(gs_error_rangecheck);
1662
    return copy_glyph_data(font, glyph, copied, options, &gdata, prefix, fdbytes);
1663
}
1664
 
1665
private const gs_copied_font_procs_t copied_procs_cid0 = {
1666
    copy_font_cid0, copy_glyph_cid0, copied_no_add_encoding,
1667
    named_glyph_slot_none,
1668
    gs_no_encode_char, copied_cid0_glyph_info, copied_cid0_glyph_outline
1669
};
1670
 
1671
private int
1672
same_cid0_hinting(const gs_font_cid0 *cfont, const gs_font_cid0 *ofont)
1673
{
1674
    int i;
1675
 
1676
    if (cfont->cidata.FDArray_size != ofont->cidata.FDArray_size)
1677
	return 0;
1678
 
1679
    for (i = 0; i < cfont->cidata.FDArray_size; i++) {
1680
	gs_font_type1 *subfont0 = cfont->cidata.FDArray[i];
1681
	gs_font_type1 *subfont1 = ofont->cidata.FDArray[i];
1682
	if (!same_type1_hinting(subfont0, subfont1))
1683
	    return 0;
1684
    }
1685
    return 1;
1686
}
1687
 
1688
/* ------ CIDFontType 2 ------ */
1689
 
1690
private int
1691
copied_cid2_CIDMap_proc(gs_font_cid2 *fcid2, gs_glyph glyph)
1692
{
1693
    uint cid = glyph - GS_MIN_CID_GLYPH;
1694
    gs_copied_font_data_t *const cfdata = cf_data((gs_font *)fcid2);
1695
    const ushort *CIDMap = cfdata->CIDMap;
1696
 
1697
    if (glyph < GS_MIN_CID_GLYPH || cid >= fcid2->cidata.common.CIDCount)
1698
	return_error(gs_error_rangecheck);
1699
    if (CIDMap[cid] == 0xffff)
1700
	return -1;	
1701
    return CIDMap[cid];
1702
}
1703
 
1704
private uint
1705
copied_cid2_get_glyph_index(gs_font_type42 *font, gs_glyph glyph)
1706
{
1707
    int glyph_index = copied_cid2_CIDMap_proc((gs_font_cid2 *)font, glyph);
1708
 
1709
    if (glyph_index < 0)
1710
	return GS_NO_GLYPH;
1711
    return glyph_index;
1712
}
1713
 
1714
private int
1715
copy_font_cid2(gs_font *font, gs_font *copied)
1716
{
1717
    gs_font_cid2 *copied2 = (gs_font_cid2 *)copied;
1718
    gs_copied_font_data_t *const cfdata = cf_data(copied);
1719
    int code;
1720
    int CIDCount = copied2->cidata.common.CIDCount;
1721
    ushort *CIDMap = (ushort *)
1722
	gs_alloc_byte_array(copied->memory, CIDCount, sizeof(ushort),
1723
			    "copy_font_cid2(CIDMap");
1724
 
1725
    if (CIDMap == 0)
1726
	return_error(gs_error_VMerror);
1727
    code = copy_font_cid_common(font, copied, &copied2->cidata.common);
1728
    if (code < 0 ||
1729
	(code = copy_font_type42(font, copied)) < 0
1730
	) {
1731
	gs_free_object(copied->memory, CIDMap, "copy_font_cid2(CIDMap");
1732
	return code;
1733
    }
1734
    cfdata->notdef = GS_MIN_CID_GLYPH;
1735
    memset(CIDMap, 0xff, CIDCount * sizeof(*CIDMap));
1736
    cfdata->CIDMap = CIDMap;
1737
    copied2->cidata.MetricsCount = 0;
1738
    copied2->cidata.CIDMap_proc = copied_cid2_CIDMap_proc;
1739
    {
1740
	gs_font_type42 *const copied42 = (gs_font_type42 *)copied;
1741
 
1742
	copied42->data.get_glyph_index = copied_cid2_get_glyph_index;
1743
    }
1744
    return 0;
1745
}
1746
 
1747
private int expand_CIDMap(gs_font_cid2 *copied2, uint CIDCount)
1748
{
1749
    ushort *CIDMap;
1750
    gs_copied_font_data_t *const cfdata = cf_data((gs_font *)copied2);
1751
 
1752
    if (CIDCount <= copied2->cidata.common.CIDCount)
1753
	return 0;
1754
    CIDMap = (ushort *)
1755
	gs_alloc_byte_array(copied2->memory, CIDCount, sizeof(ushort),
1756
			    "copy_font_cid2(CIDMap");
1757
    if (CIDMap == 0)
1758
	return_error(gs_error_VMerror);
1759
    memcpy(CIDMap, cfdata->CIDMap, copied2->cidata.common.CIDCount * sizeof(*CIDMap));
1760
    memset(CIDMap + copied2->cidata.common.CIDCount, 0xFF, 
1761
	    (CIDCount - copied2->cidata.common.CIDCount) * sizeof(*CIDMap));
1762
    cfdata->CIDMap = CIDMap;
1763
    copied2->cidata.common.CIDCount = CIDCount;
1764
    return 0;
1765
}
1766
 
1767
private int
1768
copy_glyph_cid2(gs_font *font, gs_glyph glyph, gs_font *copied, int options)
1769
{
1770
    gs_font_cid2 *fcid2 = (gs_font_cid2 *)font;
1771
    gs_copied_font_data_t *const cfdata = cf_data(copied);
1772
    gs_font_cid2 *copied2 = (gs_font_cid2 *)copied;
1773
    int gid;
1774
    int code;
1775
 
1776
    if (!(options & COPY_GLYPH_BY_INDEX)) {
1777
	uint cid = glyph - GS_MIN_CID_GLYPH;
1778
	int CIDCount;
1779
 
1780
	code = expand_CIDMap(copied2, cid + 1);
1781
	if (code < 0)
1782
	    return code;
1783
	CIDCount = copied2->cidata.common.CIDCount;
1784
        gid = fcid2->cidata.CIDMap_proc(fcid2, glyph);
1785
	if (gid < 0 || gid >= cfdata->glyphs_size)
1786
	    return_error(gs_error_rangecheck);
1787
	if (cid > CIDCount)
1788
	    return_error(gs_error_invalidaccess);
1789
	if (cfdata->CIDMap[cid] != 0xffff && cfdata->CIDMap[cid] != gid)
1790
	    return_error(gs_error_invalidaccess);
1791
	code = copy_glyph_type42(font, glyph, copied, options);
1792
	if (code < 0)
1793
	    return code;
1794
        cfdata->CIDMap[cid] = gid;
1795
    } else {
1796
	gid = glyph - GS_MIN_GLYPH_INDEX;
1797
	if (gid < 0 || gid >= cfdata->glyphs_size)
1798
	    return_error(gs_error_rangecheck);
1799
	code = copy_glyph_type42(font, glyph, copied, options);
1800
	if (code < 0)
1801
	    return code;
1802
    }
1803
    return code;
1804
}
1805
 
1806
private const gs_copied_font_procs_t copied_procs_cid2 = {
1807
    copy_font_cid2, copy_glyph_cid2, copied_no_add_encoding,
1808
    named_glyph_slot_none,
1809
    gs_no_encode_char, gs_type42_glyph_info, gs_type42_glyph_outline
1810
};
1811
 
1812
private int
1813
same_cid2_hinting(const gs_font_cid2 *cfont, const gs_font_cid2 *ofont)
1814
{
1815
    return same_type42_hinting((gs_font_type42 *)cfont, (gs_font_type42 *)ofont);
1816
}
1817
 
1818
/* ---------------- Public ---------------- */
1819
 
1820
/*
1821
 * Procedure vector for copied fonts.
1822
 */
1823
private font_proc_font_info(copied_font_info);
1824
private font_proc_enumerate_glyph(copied_enumerate_glyph);
1825
private const gs_font_procs copied_font_procs = {
1826
    0,				/* define_font, not supported */
1827
    0,				/* make_font, not supported */
1828
    copied_font_info,
1829
    gs_default_same_font,
1830
    0,				/* encode_char, varies by FontType */
1831
    0,				/* decode_char, not supported */
1832
    copied_enumerate_glyph,
1833
    0,				/* glyph_info, varies by FontType */
1834
    0,				/* glyph_outline, varies by FontType */
1835
    copied_glyph_name,
1836
    gs_default_init_fstack,
1837
    gs_default_next_char_glyph,
1838
    copied_build_char
1839
};
1840
 
1841
#if GLYPHS_SIZE_IS_PRIME
1842
private const int some_primes[] = {
1843
    /* Arbitrary choosen prime numbers, being reasonable for a Type 1|2 font size. 
1844
       We start with 257 to fit 256 glyphs and .notdef .
1845
       Smaller numbers aren't useful, because we don't know whether a font
1846
       will add more glyphs incrementally when we allocate its stable copy.
1847
    */
1848
    257, 359, 521, 769, 1031, 2053, 
1849
    3079, 4099, 5101, 6101, 7109, 8209, 10007, 12007, 14009, 
1850
    16411, 20107, 26501, 32771, 48857, 65537};
1851
#endif
1852
 
1853
/*
1854
 * Copy a font, aside from its glyphs.
1855
 */
1856
int
1857
gs_copy_font(gs_font *font, const gs_matrix *orig_matrix, gs_memory_t *mem, gs_font **pfont_new)
1858
{
1859
    gs_memory_type_ptr_t fstype = gs_object_type(font->memory, font);
1860
    uint fssize = gs_struct_type_size(fstype);
1861
    gs_font *copied = 0;
1862
    gs_copied_font_data_t *cfdata = 0;
1863
    gs_font_info_t info;
1864
    gs_copied_glyph_t *glyphs = 0;
1865
    uint glyphs_size;
1866
    gs_copied_glyph_name_t *names = 0;
1867
    bool have_names = false;
1868
    const gs_copied_font_procs_t *procs;
1869
    int code;
1870
 
1871
    /*
1872
     * Check for a supported FontType, and compute the size of its
1873
     * copied glyph table.
1874
     */
1875
    switch (font->FontType) {
1876
    case ft_TrueType:
1877
	procs = &copied_procs_type42;
1878
	glyphs_size = ((gs_font_type42 *)font)->data.trueNumGlyphs;
1879
	have_names = true;
1880
	break;
1881
    case ft_encrypted:
1882
    case ft_encrypted2:
1883
	procs = &copied_procs_type1;
1884
	/* Count the glyphs. */
1885
	glyphs_size = 0;
1886
	{
1887
	    int index = 0;
1888
	    gs_glyph glyph;
1889
 
1890
	    while (font->procs.enumerate_glyph(font, &index, GLYPH_SPACE_NAME,
1891
					       &glyph), index != 0)
1892
		++glyphs_size;
1893
	}
1894
#if GLYPHS_SIZE_IS_PRIME
1895
	/*
1896
	 * Make glyphs_size a prime number to ensure termination of the loop in
1897
	 * named_glyphs_slot_hashed, q.v.
1898
	 * Also reserve additional slots for the case of font merging and
1899
	 * for possible font increments.
1900
	 */
1901
	glyphs_size = glyphs_size * 3 / 2;
1902
	if (glyphs_size < 257)
1903
	    glyphs_size = 257;
1904
	{ int i;
1905
	    for (i = 0; i < count_of(some_primes); i++)
1906
		if (glyphs_size <= some_primes[i])
1907
		    break;
1908
	    if (i >= count_of(some_primes))
1909
		return_error(gs_error_rangecheck);
1910
	    glyphs_size = some_primes[i];
1911
	}
1912
#else
1913
	/*
1914
	 * Make names_size a power of 2 to ensure termination of the loop in
1915
	 * named_glyphs_slot_hashed, q.v.
1916
	 */
1917
	glyphs_size = glyphs_size * 3 / 2;
1918
	while (glyphs_size & (glyphs_size - 1))
1919
	    glyphs_size = (glyphs_size | (glyphs_size - 1)) + 1;
1920
	if (glyphs_size < 256)	/* probably incremental font */
1921
	    glyphs_size = 256;
1922
#endif
1923
	have_names = true;
1924
	break;
1925
    case ft_CID_encrypted:
1926
	procs = &copied_procs_cid0;
1927
	glyphs_size = ((gs_font_cid0 *)font)->cidata.common.CIDCount;
1928
	break;
1929
    case ft_CID_TrueType:
1930
	procs = &copied_procs_cid2;
1931
	/* Glyphs are indexed by GID, not by CID. */
1932
	glyphs_size = ((gs_font_cid2 *)font)->data.trueNumGlyphs;
1933
	break;
1934
    default:
1935
	return_error(gs_error_rangecheck);
1936
    }
1937
 
1938
    /* Get the font_info for copying. */
1939
 
1940
    memset(&info, 0, sizeof(info));
1941
    info.Flags_requested = ~0;
1942
    code = font->procs.font_info(font, NULL, ~0, &info);
1943
    if (code < 0)
1944
	return code;
1945
 
1946
    /* Allocate the generic copied information. */
1947
 
1948
    glyphs = gs_alloc_struct_array(mem, glyphs_size, gs_copied_glyph_t,
1949
				   &st_gs_copied_glyph_element,
1950
				   "gs_copy_font(glyphs)");
1951
    if (have_names != 0)
1952
	names = gs_alloc_struct_array(mem, glyphs_size, gs_copied_glyph_name_t,
1953
				      &st_gs_copied_glyph_name_element,
1954
				      "gs_copy_font(names)");
1955
    copied = gs_alloc_struct(mem, gs_font, fstype,
1956
			     "gs_copy_font(copied font)");
1957
    cfdata = gs_alloc_struct(mem, gs_copied_font_data_t,
1958
			    &st_gs_copied_font_data,
1959
			    "gs_copy_font(wrapper data)");
1960
    if (cfdata)
1961
	memset(cfdata, 0, sizeof(*cfdata));
1962
    if (glyphs == 0 || (names == 0 && have_names) || copied == 0 ||
1963
	cfdata == 0
1964
	) {
1965
	code = gs_note_error(gs_error_VMerror);
1966
	goto fail;
1967
    }
1968
    cfdata->info = info;
1969
    cfdata->dir = font->dir;
1970
    if ((code = (copy_string(mem, &cfdata->info.Copyright,
1971
			     "gs_copy_font(Copyright)") |
1972
		 copy_string(mem, &cfdata->info.Notice,
1973
			     "gs_copy_font(Notice)") |
1974
		 copy_string(mem, &cfdata->info.FamilyName,
1975
			     "gs_copy_font(FamilyName)") |
1976
		 copy_string(mem, &cfdata->info.FullName,
1977
			     "gs_copy_font(FullName)"))) < 0
1978
	)
1979
	goto fail;
1980
 
1981
    /* Initialize the copied font. */
1982
 
1983
    memcpy(copied, font, fssize);
1984
    copied->next = copied->prev = 0;
1985
    copied->memory = mem;
1986
    copied->is_resource = false;
1987
    gs_notify_init(&copied->notify_list, mem);
1988
    copied->base = copied;
1989
    copied->FontMatrix = *orig_matrix;
1990
    copied->client_data = cfdata;
1991
    copied->procs = copied_font_procs;
1992
    copied->procs.encode_char = procs->encode_char;
1993
    copied->procs.glyph_info = procs->glyph_info;
1994
    copied->procs.glyph_outline = procs->glyph_outline;
1995
    {
1996
	gs_font_base *bfont = (gs_font_base *)copied;
1997
 
1998
	bfont->FAPI = 0;
1999
	bfont->FAPI_font_data = 0;
2000
	bfont->encoding_index = ENCODING_INDEX_UNKNOWN;
2001
	code = uid_copy(&bfont->UID, mem, "gs_copy_font(UID)");
2002
	if (code < 0)
2003
	    goto fail;
2004
    }
2005
 
2006
    cfdata->procs = procs;
2007
    memset(glyphs, 0, glyphs_size * sizeof(*glyphs));
2008
    cfdata->glyphs = glyphs;
2009
    cfdata->glyphs_size = glyphs_size;
2010
    cfdata->num_glyphs = 0;
2011
    if (names)
2012
	memset(names, 0, glyphs_size * sizeof(*names));
2013
    cfdata->names = names;
2014
    if (names != 0) {
2015
	uint i;
2016
 
2017
	for (i = 0; i < glyphs_size; ++i)
2018
	    names[i].glyph = GS_NO_GLYPH;
2019
    }
2020
 
2021
    /* Do FontType-specific initialization. */
2022
 
2023
    code = procs->finish_copy_font(font, copied);
2024
    if (code < 0)
2025
	goto fail;
2026
 
2027
    *pfont_new = copied;
2028
    if (cfdata->notdef != GS_NO_GLYPH)
2029
	code = gs_copy_glyph(font, cfdata->notdef, copied);
2030
    return code;
2031
 
2032
 fail:
2033
    /* Free storage and exit. */
2034
    if (cfdata) {
2035
	uncopy_string(mem, &cfdata->info.FullName,
2036
		      "gs_copy_font(FullName)");
2037
	uncopy_string(mem, &cfdata->info.FamilyName,
2038
		      "gs_copy_font(FamilyName)");
2039
	uncopy_string(mem, &cfdata->info.Notice,
2040
		      "gs_copy_font(Notice)");
2041
	uncopy_string(mem, &cfdata->info.Copyright,
2042
		      "gs_copy_font(Copyright)");
2043
	gs_free_object(mem, cfdata, "gs_copy_font(wrapper data)");
2044
    }
2045
    gs_free_object(mem, copied, "gs_copy_font(copied font)");
2046
    gs_free_object(mem, names, "gs_copy_font(names)");
2047
    gs_free_object(mem, glyphs, "gs_copy_font(glyphs)");
2048
    return code;
2049
}
2050
 
2051
/*
2052
 * Copy a glyph, including any sub-glyphs.
2053
 */
2054
int
2055
gs_copy_glyph(gs_font *font, gs_glyph glyph, gs_font *copied)
2056
{
2057
    return gs_copy_glyph_options(font, glyph, copied, 0);
2058
}
2059
int
2060
gs_copy_glyph_options(gs_font *font, gs_glyph glyph, gs_font *copied,
2061
		      int options)
2062
{
2063
    int code;
2064
#define MAX_GLYPH_PIECES 64	/* arbitrary, but 32 is too small - bug 687698. */
2065
    gs_glyph glyphs[MAX_GLYPH_PIECES];
2066
    uint count = 1, i;
2067
 
2068
    if (copied->procs.font_info != copied_font_info)
2069
	return_error(gs_error_rangecheck);
2070
    code = cf_data(copied)->procs->copy_glyph(font, glyph, copied, options);
2071
    if (code != 0)
2072
	return code;
2073
    /* Copy any sub-glyphs. */
2074
    glyphs[0] = glyph;
2075
    code = psf_add_subset_pieces(glyphs, &count, MAX_GLYPH_PIECES, MAX_GLYPH_PIECES,
2076
			  font);
2077
    if (code < 0)
2078
	return code;
2079
    if (count > MAX_GLYPH_PIECES)
2080
	return_error(gs_error_limitcheck);
2081
    for (i = 1; i < count; ++i) {
2082
	code = gs_copy_glyph_options(font, glyphs[i], copied,
2083
				     (options & ~COPY_GLYPH_NO_OLD) | COPY_GLYPH_BY_INDEX);
2084
	if (code < 0)
2085
	    return code;
2086
    }
2087
    /*
2088
     * Because 'seac' accesses the Encoding of the font as well as the
2089
     * glyphs, we have to copy the Encoding entries as well.
2090
     */
2091
    if (count == 1)
2092
	return 0;
2093
    switch (font->FontType) {
2094
    case ft_encrypted:
2095
    case ft_encrypted2:
2096
	break;
2097
    default:
2098
	return 0;
2099
    }
2100
#if 0 /* No need to add subglyphs to the Encoding because they always are 
2101
	 taken from StandardEncoding (See the Type 1 spec about 'seac').
2102
	 Attempt to add them to the encoding can cause a conflict,
2103
	 if the encoding specifies different glyphs for these char codes
2104
	 (See the bug #687172). */
2105
    {
2106
	gs_copied_glyph_t *pcg;
2107
	gs_glyph_data_t gdata;
2108
	gs_char chars[2];
2109
 
2110
	gdata.memory = font->memory;
2111
	/* Since we just copied the glyph, copied_glyph_slot can't fail. */
2112
	DISCARD(copied_glyph_slot(cf_data(copied), glyph, &pcg));
2113
	gs_glyph_data_from_string(&gdata, pcg->gdata.data, pcg->gdata.size,
2114
				  NULL);
2115
	code = gs_type1_piece_codes((gs_font_type1 *)font, &gdata, chars);
2116
	if (code <= 0 ||	/* 0 is not possible here */
2117
	    (code = gs_copied_font_add_encoding(copied, chars[0], glyphs[1])) < 0 ||
2118
	    (code = gs_copied_font_add_encoding(copied, chars[1], glyphs[2])) < 0
2119
	    )
2120
	    return code;
2121
    }
2122
#endif
2123
    return 0;
2124
#undef MAX_GLYPH_PIECES
2125
}
2126
 
2127
/*
2128
 * Add an Encoding entry to a copied font.  The glyph need not already have
2129
 * been copied.
2130
 */
2131
int
2132
gs_copied_font_add_encoding(gs_font *copied, gs_char chr, gs_glyph glyph)
2133
{
2134
    gs_copied_font_data_t *const cfdata = cf_data(copied);
2135
 
2136
    if (copied->procs.font_info != copied_font_info)
2137
	return_error(gs_error_rangecheck);
2138
    return cfdata->procs->add_encoding(copied, chr, glyph);
2139
}
2140
 
2141
/*
2142
 * Copy all the glyphs and, if relevant, Encoding entries from a font.  This
2143
 * is equivalent to copying the glyphs and Encoding entries individually,
2144
 * and returns errors under the same conditions.
2145
 */
2146
int
2147
gs_copy_font_complete(gs_font *font, gs_font *copied)
2148
{
2149
    int index, code = 0;
2150
    gs_glyph_space_t space = GLYPH_SPACE_NAME;
2151
    gs_glyph glyph;
2152
 
2153
    /*
2154
     * For Type 1 fonts and CIDFonts, enumerating the glyphs using
2155
     * GLYPH_SPACE_NAME will cover all the glyphs.  (The "names" of glyphs
2156
     * in CIDFonts are CIDs, but that is not a problem.)  For Type 42 fonts,
2157
     * however, we have to copy by name once, so that we also copy the
2158
     * name-to-GID mapping (the CharStrings dictionary in PostScript), and
2159
     * then copy again by GID, to cover glyphs that don't have names.
2160
     */
2161
    for (;;) {
2162
	for (index = 0;
2163
	     code >= 0 &&
2164
		 (font->procs.enumerate_glyph(font, &index, space, &glyph),
2165
		  index != 0);
2166
	     )
2167
	    code = gs_copy_glyph(font, glyph, copied);
2168
	/* For Type 42 fonts, if we copied by name, now copy again by index. */
2169
	if (space == GLYPH_SPACE_NAME && font->FontType == ft_TrueType)
2170
	    space = GLYPH_SPACE_INDEX;
2171
	else
2172
	    break;
2173
    }
2174
    if (cf_data(copied)->Encoding != 0)
2175
	for (index = 0; code >= 0 && index < 256; ++index) {
2176
	    glyph = font->procs.encode_char(font, (gs_char)index,
2177
					    GLYPH_SPACE_NAME);
2178
	    if (glyph != GS_NO_GLYPH)
2179
		code = gs_copied_font_add_encoding(copied, (gs_char)index,
2180
						   glyph);
2181
	}
2182
    if (copied->FontType != ft_composite) {
2183
	gs_font_base *bfont = (gs_font_base *)font;
2184
	gs_font_base *bcopied = (gs_font_base *)copied;
2185
 
2186
	bcopied->encoding_index = bfont->encoding_index;
2187
	bcopied->nearest_encoding_index = bfont->nearest_encoding_index;
2188
    }
2189
    return code;
2190
}
2191
 
2192
/*
2193
 * Check whether specified glyphs can be copied from another font.
2194
 * It means that (1) fonts have same hinting parameters and 
2195
 * (2) font subsets for the specified glyph set don't include different 
2196
 * outlines or metrics. Possible returned values : 
2197
 * 0 (incompatible), 1 (compatible), < 0 (error)
2198
 */
2199
int
2200
gs_copied_can_copy_glyphs(const gs_font *cfont, const gs_font *ofont, 
2201
			  gs_glyph *glyphs, int num_glyphs, int glyphs_step,
2202
			  bool check_hinting)
2203
{   
2204
    int code = 0;
2205
 
2206
    if (cfont == ofont)
2207
	return 1;
2208
    if (cfont->FontType != ofont->FontType)
2209
	return 0;
2210
    if (cfont->WMode != ofont->WMode)
2211
	return 0;
2212
    if (cfont->font_name.size == 0 || ofont->font_name.size == 0) {
2213
	if (cfont->key_name.size != ofont->key_name.size ||
2214
	    memcmp(cfont->key_name.chars, ofont->key_name.chars, 
2215
			cfont->font_name.size))
2216
    	    return 0; /* Don't allow to merge random fonts. */
2217
    } else {
2218
	if (cfont->font_name.size != ofont->font_name.size ||
2219
	    memcmp(cfont->font_name.chars, ofont->font_name.chars, 
2220
			    cfont->font_name.size))
2221
	    return 0; /* Don't allow to merge random fonts. */
2222
    }
2223
    if (check_hinting) {
2224
	switch(cfont->FontType) {
2225
	    case ft_encrypted:
2226
	    case ft_encrypted2:
2227
		if (!same_type1_hinting((const gs_font_type1 *)cfont, 
2228
					(const gs_font_type1 *)ofont))
2229
		    return 0;
2230
		code = 1;
2231
		break;
2232
	    case ft_TrueType:
2233
		code = same_type42_hinting((gs_font_type42 *)cfont, 
2234
					(gs_font_type42 *)ofont);
2235
		break;
2236
	    case ft_CID_encrypted:
2237
		if (!gs_is_CIDSystemInfo_compatible(
2238
				gs_font_cid_system_info(cfont), 
2239
				gs_font_cid_system_info(ofont)))
2240
		    return 0;
2241
		code = same_cid0_hinting((const gs_font_cid0 *)cfont, 
2242
					 (const gs_font_cid0 *)ofont);
2243
		break;
2244
	    case ft_CID_TrueType:
2245
		if (!gs_is_CIDSystemInfo_compatible(
2246
				gs_font_cid_system_info(cfont), 
2247
				gs_font_cid_system_info(ofont)))
2248
		    return 0;
2249
		code = same_cid2_hinting((const gs_font_cid2 *)cfont, 
2250
					 (const gs_font_cid2 *)ofont);
2251
		break;
2252
	    default:
2253
		return_error(gs_error_unregistered); /* Must not happen. */
2254
	}
2255
	if (code <= 0) /* an error or false */
2256
	    return code; 
2257
    }
2258
    return compare_glyphs(cfont, ofont, glyphs, num_glyphs, glyphs_step, 0);
2259
}
2260
 
2261
/* Extension glyphs may be added to a font to resolve 
2262
   glyph name conflicts while conwerting a PDF Widths into Metrics.
2263
   This function drops them before writing out an embedded font. */
2264
int
2265
copied_drop_extension_glyphs(gs_font *copied)
2266
{
2267
    /* 	Note : This function drops 'used' flags for some glyphs
2268
	and truncates glyph names. Can't use the font
2269
	for outlining|rasterization|width after applying it.
2270
     */
2271
    gs_copied_font_data_t *const cfdata = cf_data(copied);
2272
    uint gsize = cfdata->glyphs_size, i;
2273
    const int sl = strlen(gx_extendeg_glyph_name_separator);
2274
 
2275
    for (i = 0; i < gsize; i++) {
2276
	gs_copied_glyph_t *pslot = &cfdata->glyphs[i];
2277
	gs_copied_glyph_name_t *name;
2278
	int l, j, k, i0;
2279
 
2280
	if (!pslot->used)
2281
	    continue;
2282
	name = &cfdata->names[i];
2283
	l = name->str.size - sl, j;
2284
 
2285
	for (j = 0; j < l; j ++)
2286
	    if (!memcmp(gx_extendeg_glyph_name_separator, name->str.data + j, sl))
2287
		break;
2288
	if (j >= l)
2289
	    continue;
2290
	/* Found an extension name.
2291
	   Find the corresponding non-extended one. */
2292
	i0 = i;
2293
	for (k = 0; k < gsize; k++)
2294
	    if (cfdata->glyphs[k].used && 
2295
		    cfdata->names[k].str.size == j &&
2296
		    !memcmp(cfdata->names[k].str.data, name->str.data, j) &&
2297
		    !bytes_compare(pslot->gdata.data, pslot->gdata.size,
2298
			    cfdata->glyphs[k].gdata.data, cfdata->glyphs[k].gdata.size)) {
2299
		i0 = k;
2300
		break;
2301
	    }
2302
	/* Truncate the extended glyph name. */
2303
	cfdata->names[i0].str.size = j;
2304
	/* Drop others with same prefix. */
2305
	for (k = 0; k < gsize; k++)
2306
	    if (k != i0 && cfdata->glyphs[k].used && 
2307
		    cfdata->names[k].str.size >= j + sl &&
2308
		    !memcmp(cfdata->names[k].str.data, name->str.data, j) &&
2309
		    !memcmp(gx_extendeg_glyph_name_separator, name + j, sl) &&
2310
		    !bytes_compare(pslot->gdata.data, pslot->gdata.size,
2311
			    cfdata->glyphs[k].gdata.data, cfdata->glyphs[k].gdata.size))
2312
		cfdata->glyphs[k].used = false;
2313
    }
2314
    return 0;
2315
}