1
4
5# include "luametatex.h"
6
7
8
9
19
20node_memory_state_info lmt_node_memory_state = {
21 .nodes = NULL,
22 .nodesizes = NULL,
23 .free_chain = { null },
24 .nodes_data = {
25 .minimum = min_node_size,
26 .maximum = max_node_size,
27 .size = siz_node_size,
28 .step = stp_node_size,
29 .allocated = 0,
30 .itemsize = sizeof(memoryword) + sizeof(char),
31 .top = 0,
32 .ptr = 0,
33 .initial = 0,
34 .offset = 0,
35 },
36 .extra_data = {
37 .minimum = memory_data_unset,
38 .maximum = memory_data_unset,
39 .size = memory_data_unset,
40 .step = memory_data_unset,
41 .allocated = 0,
42 .itemsize = 1,
43 .top = 0,
44 .ptr = 0,
45 .initial = memory_data_unset,
46 .offset = 0,
47 },
48 .reserved = 0,
49 .padding = 0,
50 .node_properties_id = 0,
51 .lua_properties_level = 0,
52 .attribute_cache = 0,
53 .max_used_attribute = 1,
54 .node_properties_table_size = 0,
55};
56
57
58
59static void tex_aux_check_node (halfword node);
60static halfword tex_aux_allocated_node (int size);
61
62
81
82void lmt_nodelib_initialize(void) {
83
84
85
86 value_info
87 *subtypes_dir, *subtypes_par, *subtypes_glue, *subtypes_boundary, *subtypes_penalty, *subtypes_kern,
88 *subtypes_rule, *subtypes_glyph , *subtypes_disc, *subtypes_list, *subtypes_adjust, *subtypes_mark,
89 *subtypes_math, *subtypes_noad, *subtypes_radical, *subtypes_choice, *subtypes_accent, *subtypes_fence, *subtypes_split,
90 *subtypes_attribute;
91
92 value_info
93 *lmt_node_fields_accent, *lmt_node_fields_adjust, *lmt_node_fields_attribute,
94 *lmt_node_fields_boundary, *lmt_node_fields_choice, *lmt_node_fields_delimiter, *lmt_node_fields_dir,
95 *lmt_node_fields_disc, *lmt_node_fields_fence, *lmt_node_fields_fraction, *lmt_node_fields_glue,
96 *lmt_node_fields_glue_spec, *lmt_node_fields_glyph, *lmt_node_fields_insert, *lmt_node_fields_split,
97 *lmt_node_fields_kern, *lmt_node_fields_list, *lmt_node_fields_par, *lmt_node_fields_mark, *lmt_node_fields_math,
98 *lmt_node_fields_math_char, *lmt_node_fields_math_text_char, *lmt_node_fields_noad, *lmt_node_fields_penalty,
99 *lmt_node_fields_radical, *lmt_node_fields_rule, *lmt_node_fields_style, *lmt_node_fields_parameter,
100 *lmt_node_fields_sub_box, *lmt_node_fields_sub_mlist, *lmt_node_fields_unset, *lmt_node_fields_whatsit;
101
102 subtypes_dir = lmt_aux_allocate_value_info(cancel_dir_subtype);
103
104 set_value_entry_key(subtypes_dir, normal_dir_subtype, normal)
105 set_value_entry_key(subtypes_dir, cancel_dir_subtype, cancel)
106
107 subtypes_split = lmt_aux_allocate_value_info(insert_split_subtype);
108
109 set_value_entry_key(subtypes_split, normal_split_subtype, normal)
110 set_value_entry_key(subtypes_split, insert_split_subtype, insert)
111
112 subtypes_par = lmt_aux_allocate_value_info(math_par_subtype);
113
114 set_value_entry_key(subtypes_par, vmode_par_par_subtype, vmodepar)
115 set_value_entry_key(subtypes_par, local_box_par_subtype, localbox)
116 set_value_entry_key(subtypes_par, hmode_par_par_subtype, hmodepar)
117 set_value_entry_key(subtypes_par, parameter_par_subtype, parameter)
118 set_value_entry_key(subtypes_par, math_par_subtype, math)
119
120 subtypes_glue = lmt_aux_allocate_value_info(u_leaders);
121
122 set_value_entry_key(subtypes_glue, user_skip_glue, userskip)
123 set_value_entry_key(subtypes_glue, line_skip_glue, lineskip)
124 set_value_entry_key(subtypes_glue, baseline_skip_glue, baselineskip)
125 set_value_entry_key(subtypes_glue, par_skip_glue, parskip)
126 set_value_entry_key(subtypes_glue, above_display_skip_glue, abovedisplayskip)
127 set_value_entry_key(subtypes_glue, below_display_skip_glue, belowdisplayskip)
128 set_value_entry_key(subtypes_glue, above_display_short_skip_glue, abovedisplayshortskip)
129 set_value_entry_key(subtypes_glue, below_display_short_skip_glue, belowdisplayshortskip)
130 set_value_entry_key(subtypes_glue, left_skip_glue, leftskip)
131 set_value_entry_key(subtypes_glue, right_skip_glue, rightskip)
132 set_value_entry_key(subtypes_glue, top_skip_glue, topskip)
133 set_value_entry_key(subtypes_glue, split_top_skip_glue, splittopskip)
134 set_value_entry_key(subtypes_glue, tab_skip_glue, tabskip)
135 set_value_entry_key(subtypes_glue, space_skip_glue, spaceskip)
136 set_value_entry_key(subtypes_glue, xspace_skip_glue, xspaceskip)
137 set_value_entry_key(subtypes_glue, zero_space_skip_glue, zerospaceskip)
138 set_value_entry_key(subtypes_glue, par_fill_left_skip_glue, parfillleftskip)
139 set_value_entry_key(subtypes_glue, par_fill_right_skip_glue, parfillskip)
140 set_value_entry_key(subtypes_glue, par_init_left_skip_glue, parinitleftskip)
141 set_value_entry_key(subtypes_glue, par_init_right_skip_glue, parinitrightskip)
142 set_value_entry_key(subtypes_glue, indent_skip_glue, indentskip)
143 set_value_entry_key(subtypes_glue, left_hang_skip_glue, lefthangskip)
144 set_value_entry_key(subtypes_glue, right_hang_skip_glue, righthangskip)
145 set_value_entry_key(subtypes_glue, correction_skip_glue, correctionskip)
146 set_value_entry_key(subtypes_glue, inter_math_skip_glue, intermathskip)
147 set_value_entry_key(subtypes_glue, ignored_glue, ignored)
148 set_value_entry_key(subtypes_glue, page_glue, page)
149 set_value_entry_key(subtypes_glue, math_skip_glue, mathskip)
150 set_value_entry_key(subtypes_glue, thin_mu_skip_glue, thinmuskip)
151 set_value_entry_key(subtypes_glue, med_mu_skip_glue, medmuskip)
152 set_value_entry_key(subtypes_glue, thick_mu_skip_glue, thickmuskip)
153 set_value_entry_key(subtypes_glue, conditional_math_glue, conditionalmathskip)
154 set_value_entry_key(subtypes_glue, rulebased_math_glue, rulebasedmathskip)
155 set_value_entry_key(subtypes_glue, mu_glue, muglue)
156 set_value_entry_key(subtypes_glue, a_leaders, leaders)
157 set_value_entry_key(subtypes_glue, c_leaders, cleaders)
158 set_value_entry_key(subtypes_glue, x_leaders, xleaders)
159 set_value_entry_key(subtypes_glue, g_leaders, gleaders)
160 set_value_entry_key(subtypes_glue, u_leaders, uleaders)
161
162 subtypes_boundary = lmt_aux_allocate_value_info(math_boundary);
163
164 set_value_entry_key(subtypes_boundary, cancel_boundary, cancel)
165 set_value_entry_key(subtypes_boundary, user_boundary, user)
166 set_value_entry_key(subtypes_boundary, protrusion_boundary, protrusion)
167 set_value_entry_key(subtypes_boundary, word_boundary, word)
168 set_value_entry_key(subtypes_boundary, page_boundary, page)
169 set_value_entry_key(subtypes_boundary, math_boundary, math)
170
171
172 subtypes_penalty = lmt_aux_allocate_value_info(equation_number_penalty_subtype);
173
174 set_value_entry_key(subtypes_penalty, user_penalty_subtype, userpenalty)
175 set_value_entry_key(subtypes_penalty, linebreak_penalty_subtype, linebreakpenalty)
176 set_value_entry_key(subtypes_penalty, line_penalty_subtype, linepenalty)
177 set_value_entry_key(subtypes_penalty, word_penalty_subtype, wordpenalty)
178 set_value_entry_key(subtypes_penalty, final_penalty_subtype, finalpenalty)
179 set_value_entry_key(subtypes_penalty, orphan_penalty_subtype, orphanpenalty)
180 set_value_entry_key(subtypes_penalty, single_line_penalty_subtype, singlelinepenalty)
181 set_value_entry_key(subtypes_penalty, math_pre_penalty_subtype, mathprepenalty)
182 set_value_entry_key(subtypes_penalty, math_post_penalty_subtype, mathpostpenalty)
183 set_value_entry_key(subtypes_penalty, before_display_penalty_subtype, beforedisplaypenalty)
184 set_value_entry_key(subtypes_penalty, after_display_penalty_subtype, afterdisplaypenalty)
185 set_value_entry_key(subtypes_penalty, equation_number_penalty_subtype, equationnumberpenalty)
186
187 subtypes_kern = lmt_aux_allocate_value_info(vertical_math_kern_subtype);
188
189 set_value_entry_key(subtypes_kern, font_kern_subtype, fontkern)
190 set_value_entry_key(subtypes_kern, explicit_kern_subtype, userkern)
191 set_value_entry_key(subtypes_kern, accent_kern_subtype, accentkern)
192 set_value_entry_key(subtypes_kern, italic_kern_subtype, italiccorrection)
193 set_value_entry_key(subtypes_kern, left_correction_kern_subtype, leftcorrectionkern)
194 set_value_entry_key(subtypes_kern, right_correction_kern_subtype,rightcorrectionkern)
195 set_value_entry_key(subtypes_kern, space_font_kern_subtype, spacefontkern)
196 set_value_entry_key(subtypes_kern, left_margin_kern_subtype, leftmarginkern)
197 set_value_entry_key(subtypes_kern, right_margin_kern_subtype, rightmarginkern)
198 set_value_entry_key(subtypes_kern, explicit_math_kern_subtype, mathkern)
199 set_value_entry_key(subtypes_kern, math_shape_kern_subtype, mathshapekern)
200 set_value_entry_key(subtypes_kern, horizontal_math_kern_subtype, horizontalmathkern)
201 set_value_entry_key(subtypes_kern, vertical_math_kern_subtype, verticalmathkern)
202
203 subtypes_rule = lmt_aux_allocate_value_info(image_rule_subtype);
204
205 set_value_entry_key(subtypes_rule, normal_rule_subtype, normal)
206 set_value_entry_key(subtypes_rule, empty_rule_subtype, empty)
207 set_value_entry_key(subtypes_rule, strut_rule_subtype, strut)
208 set_value_entry_key(subtypes_rule, outline_rule_subtype, outline)
209 set_value_entry_key(subtypes_rule, user_rule_subtype, user)
210 set_value_entry_key(subtypes_rule, math_over_rule_subtype, over)
211 set_value_entry_key(subtypes_rule, math_under_rule_subtype, under)
212 set_value_entry_key(subtypes_rule, math_fraction_rule_subtype, fraction)
213 set_value_entry_key(subtypes_rule, math_radical_rule_subtype, radical)
214 set_value_entry_key(subtypes_rule, box_rule_subtype, box)
215 set_value_entry_key(subtypes_rule, image_rule_subtype, image)
216 set_value_entry_key(subtypes_rule, virtual_rule_subtype, virtual)
217
218 subtypes_glyph = lmt_aux_allocate_value_info(glyph_math_accent_subtype);
219
220 set_value_entry_key(subtypes_glyph, glyph_unset_subtype, unset)
221 set_value_entry_key(subtypes_glyph, glyph_character_subtype, character)
222 set_value_entry_key(subtypes_glyph, glyph_ligature_subtype, ligature)
223 set_value_entry_key(subtypes_glyph, glyph_math_delimiter_subtype, delimiter);
224 set_value_entry_key(subtypes_glyph, glyph_math_extensible_subtype, extensible);
225 set_value_entry_key(subtypes_glyph, glyph_math_ordinary_subtype, ordinary);
226 set_value_entry_key(subtypes_glyph, glyph_math_operator_subtype, operator);
227 set_value_entry_key(subtypes_glyph, glyph_math_binary_subtype, binary);
228 set_value_entry_key(subtypes_glyph, glyph_math_relation_subtype, relation);
229 set_value_entry_key(subtypes_glyph, glyph_math_open_subtype, open);
230 set_value_entry_key(subtypes_glyph, glyph_math_close_subtype, close);
231 set_value_entry_key(subtypes_glyph, glyph_math_punctuation_subtype, punctuation);
232 set_value_entry_key(subtypes_glyph, glyph_math_variable_subtype, variable);
233 set_value_entry_key(subtypes_glyph, glyph_math_active_subtype, active);
234 set_value_entry_key(subtypes_glyph, glyph_math_inner_subtype, inner);
235 set_value_entry_key(subtypes_glyph, glyph_math_over_subtype, over);
236 set_value_entry_key(subtypes_glyph, glyph_math_under_subtype, under);
237 set_value_entry_key(subtypes_glyph, glyph_math_fraction_subtype, fraction);
238 set_value_entry_key(subtypes_glyph, glyph_math_radical_subtype, radical);
239 set_value_entry_key(subtypes_glyph, glyph_math_middle_subtype, middle);
240 set_value_entry_key(subtypes_glyph, glyph_math_accent_subtype, accent);
241
242 subtypes_disc = lmt_aux_allocate_value_info(syllable_discretionary_code);
243
244 set_value_entry_key(subtypes_disc, normal_discretionary_code, discretionary)
245 set_value_entry_key(subtypes_disc, explicit_discretionary_code, explicit)
246 set_value_entry_key(subtypes_disc, automatic_discretionary_code, automatic)
247 set_value_entry_key(subtypes_disc, mathematics_discretionary_code, math)
248 set_value_entry_key(subtypes_disc, syllable_discretionary_code, regular)
249
250 subtypes_fence = lmt_aux_allocate_value_info(no_fence_side);
251
252 set_value_entry_key(subtypes_fence, unset_fence_side, unset)
253 set_value_entry_key(subtypes_fence, left_fence_side, left)
254 set_value_entry_key(subtypes_fence, middle_fence_side, middle)
255 set_value_entry_key(subtypes_fence, right_fence_side, right)
256 set_value_entry_key(subtypes_fence, left_operator_side, operator)
257 set_value_entry_key(subtypes_fence, no_fence_side, no)
258
259 subtypes_list = lmt_aux_allocate_value_info(local_middle_list);
260
261 set_value_entry_key(subtypes_list, unknown_list, unknown)
262 set_value_entry_key(subtypes_list, line_list, line)
263 set_value_entry_key(subtypes_list, hbox_list, box)
264 set_value_entry_key(subtypes_list, indent_list, indent)
265 set_value_entry_key(subtypes_list, container_list, container)
266 set_value_entry_key(subtypes_list, align_row_list, alignment)
267 set_value_entry_key(subtypes_list, align_cell_list, cell)
268 set_value_entry_key(subtypes_list, equation_list, equation)
269 set_value_entry_key(subtypes_list, equation_number_list, equationnumber)
270 set_value_entry_key(subtypes_list, math_list_list, math)
271 set_value_entry_key(subtypes_list, math_pack_list, mathpack)
272 set_value_entry_key(subtypes_list, math_char_list, mathchar)
273 set_value_entry_key(subtypes_list, math_h_extensible_list, hextensible)
274 set_value_entry_key(subtypes_list, math_v_extensible_list, vextensible)
275 set_value_entry_key(subtypes_list, math_h_delimiter_list, hdelimiter)
276 set_value_entry_key(subtypes_list, math_v_delimiter_list, vdelimiter)
277 set_value_entry_key(subtypes_list, math_over_delimiter_list, overdelimiter)
278 set_value_entry_key(subtypes_list, math_under_delimiter_list, underdelimiter)
279 set_value_entry_key(subtypes_list, math_numerator_list, numerator)
280 set_value_entry_key(subtypes_list, math_denominator_list, denominator)
281 set_value_entry_key(subtypes_list, math_modifier_list, modifier)
282 set_value_entry_key(subtypes_list, math_fraction_list, fraction)
283 set_value_entry_key(subtypes_list, math_nucleus_list, nucleus)
284 set_value_entry_key(subtypes_list, math_sup_list, sup)
285 set_value_entry_key(subtypes_list, math_sub_list, sub)
286 set_value_entry_key(subtypes_list, math_pre_post_list, prepost)
287 set_value_entry_key(subtypes_list, math_degree_list, degree)
288 set_value_entry_key(subtypes_list, math_scripts_list, scripts)
289 set_value_entry_key(subtypes_list, math_over_list, over)
290 set_value_entry_key(subtypes_list, math_under_list, under)
291 set_value_entry_key(subtypes_list, math_accent_list, accent)
292 set_value_entry_key(subtypes_list, math_radical_list, radical)
293 set_value_entry_key(subtypes_list, math_fence_list, fence)
294 set_value_entry_key(subtypes_list, math_rule_list, rule)
295 set_value_entry_key(subtypes_list, math_ghost_list, ghost)
296 set_value_entry_key(subtypes_list, insert_result_list, insert)
297 set_value_entry_key(subtypes_list, local_list, local)
298 set_value_entry_key(subtypes_list, local_left_list, left)
299 set_value_entry_key(subtypes_list, local_right_list, right)
300 set_value_entry_key(subtypes_list, local_middle_list, middle)
301
302 subtypes_math = lmt_aux_allocate_value_info(end_inline_math);
303
304 set_value_entry_key(subtypes_math, begin_inline_math, beginmath)
305 set_value_entry_key(subtypes_math, end_inline_math, endmath)
306
307 subtypes_adjust = lmt_aux_allocate_value_info(local_adjust_code);
308
309 set_value_entry_key(subtypes_adjust, pre_adjust_code, pre)
310 set_value_entry_key(subtypes_adjust, post_adjust_code, post)
311 set_value_entry_key(subtypes_adjust, local_adjust_code, local)
312
313 subtypes_mark = lmt_aux_allocate_value_info(reset_mark_value_code);
314
315 set_value_entry_key(subtypes_mark, set_mark_value_code, set)
316 set_value_entry_key(subtypes_mark, reset_mark_value_code, reset)
317
318 subtypes_noad = lmt_aux_allocate_value_info(vcenter_noad_subtype);
319
320 set_value_entry_key(subtypes_noad, ordinary_noad_subtype, ordinary)
321 set_value_entry_key(subtypes_noad, operator_noad_subtype, operator)
322 set_value_entry_key(subtypes_noad, binary_noad_subtype, binary)
323 set_value_entry_key(subtypes_noad, relation_noad_subtype, relation)
324 set_value_entry_key(subtypes_noad, open_noad_subtype, open)
325 set_value_entry_key(subtypes_noad, close_noad_subtype, close)
326 set_value_entry_key(subtypes_noad, punctuation_noad_subtype, punctuation)
327 set_value_entry_key(subtypes_noad, variable_noad_subtype, variable)
328 set_value_entry_key(subtypes_noad, active_noad_subtype, active)
329 set_value_entry_key(subtypes_noad, inner_noad_subtype, inner)
330 set_value_entry_key(subtypes_noad, under_noad_subtype, under)
331 set_value_entry_key(subtypes_noad, over_noad_subtype, over)
332 set_value_entry_key(subtypes_noad, fraction_noad_subtype, fraction)
333 set_value_entry_key(subtypes_noad, radical_noad_subtype, radical)
334 set_value_entry_key(subtypes_noad, middle_noad_subtype, middle)
335 set_value_entry_key(subtypes_noad, accent_noad_subtype, accent)
336 set_value_entry_key(subtypes_noad, fenced_noad_subtype, fenced)
337 set_value_entry_key(subtypes_noad, ghost_noad_subtype, ghost)
338 set_value_entry_key(subtypes_noad, vcenter_noad_subtype, vcenter)
339
340 subtypes_choice = lmt_aux_allocate_value_info(discretionary_choice_subtype);
341
342 set_value_entry_key(subtypes_choice, normal_choice_subtype, normal)
343 set_value_entry_key(subtypes_choice, discretionary_choice_subtype, discretionary)
344
345 subtypes_radical = lmt_aux_allocate_value_info(h_extensible_radical_subtype);
346
347 set_value_entry_key(subtypes_radical, normal_radical_subtype, normal)
348 set_value_entry_key(subtypes_radical, radical_radical_subtype, radical)
349 set_value_entry_key(subtypes_radical, root_radical_subtype, root)
350 set_value_entry_key(subtypes_radical, rooted_radical_subtype, rooted)
351 set_value_entry_key(subtypes_radical, under_delimiter_radical_subtype, underdelimiter)
352 set_value_entry_key(subtypes_radical, over_delimiter_radical_subtype, overdelimiter)
353 set_value_entry_key(subtypes_radical, delimiter_under_radical_subtype, delimiterunder)
354 set_value_entry_key(subtypes_radical, delimiter_over_radical_subtype, delimiterover)
355 set_value_entry_key(subtypes_radical, delimited_radical_subtype, delimited)
356 set_value_entry_key(subtypes_radical, h_extensible_radical_subtype, hextensible)
357
358 subtypes_accent = lmt_aux_allocate_value_info(fixedboth_accent_subtype);
359
360 set_value_entry_key(subtypes_accent, bothflexible_accent_subtype, bothflexible)
361 set_value_entry_key(subtypes_accent, fixedtop_accent_subtype, fixedtop)
362 set_value_entry_key(subtypes_accent, fixedbottom_accent_subtype, fixedbottom)
363 set_value_entry_key(subtypes_accent, fixedboth_accent_subtype, fixedboth)
364
365 subtypes_attribute = lmt_aux_allocate_value_info(attribute_value_subtype);
366
367 set_value_entry_key(subtypes_attribute, attribute_list_subtype, list)
368 set_value_entry_key(subtypes_attribute, attribute_value_subtype, value)
369
370
371
372 lmt_node_fields_accent = lmt_aux_allocate_value_info(9);
373
374 set_value_entry_val(lmt_node_fields_accent, 0, attribute_field, attr);
375 set_value_entry_val(lmt_node_fields_accent, 1, node_list_field, nucleus);
376 set_value_entry_val(lmt_node_fields_accent, 2, node_list_field, sub);
377 set_value_entry_val(lmt_node_fields_accent, 3, node_list_field, sup);
378 set_value_entry_val(lmt_node_fields_accent, 4, node_list_field, accent);
379 set_value_entry_val(lmt_node_fields_accent, 5, node_list_field, bottomaccent);
380 set_value_entry_val(lmt_node_fields_accent, 6, node_list_field, topaccent);
381 set_value_entry_val(lmt_node_fields_accent, 7, node_list_field, overlayaccent);
382 set_value_entry_val(lmt_node_fields_accent, 8, node_list_field, fraction);
383
384 lmt_node_fields_adjust = lmt_aux_allocate_value_info(2);
385
386 set_value_entry_val(lmt_node_fields_adjust, 0, attribute_field, attr);
387 set_value_entry_val(lmt_node_fields_adjust, 1, node_list_field, list);
388
389 lmt_node_fields_attribute = lmt_aux_allocate_value_info(4);
390
391 set_value_entry_val(lmt_node_fields_attribute, 0, integer_field, count);
392 set_value_entry_val(lmt_node_fields_attribute, 1, integer_field, data);
393 set_value_entry_val(lmt_node_fields_attribute, 2, integer_field, index);
394 set_value_entry_val(lmt_node_fields_attribute, 3, integer_field, value);
395
396
397
398 lmt_node_fields_boundary = lmt_aux_allocate_value_info(2);
399
400 set_value_entry_val(lmt_node_fields_boundary, 0, attribute_field, attr);
401 set_value_entry_val(lmt_node_fields_boundary, 1, integer_field, data);
402
403 lmt_node_fields_choice = lmt_aux_allocate_value_info(5);
404
405 set_value_entry_val(lmt_node_fields_choice, 0, attribute_field, attr);
406 set_value_entry_val(lmt_node_fields_choice, 1, node_list_field, display);
407 set_value_entry_val(lmt_node_fields_choice, 2, node_list_field, text);
408 set_value_entry_val(lmt_node_fields_choice, 3, node_list_field, script);
409 set_value_entry_val(lmt_node_fields_choice, 4, node_list_field, scriptscript);
410
411 lmt_node_fields_delimiter = lmt_aux_allocate_value_info(5);
412
413 set_value_entry_val(lmt_node_fields_delimiter, 0, attribute_field, attr);
414 set_value_entry_val(lmt_node_fields_delimiter, 1, integer_field, smallfamily);
415 set_value_entry_val(lmt_node_fields_delimiter, 2, integer_field, smallchar);
416 set_value_entry_val(lmt_node_fields_delimiter, 3, integer_field, largefamily);
417 set_value_entry_val(lmt_node_fields_delimiter, 4, integer_field, largechar);
418
419 lmt_node_fields_dir = lmt_aux_allocate_value_info(3);
420
421 set_value_entry_val(lmt_node_fields_dir, 0, attribute_field, attr);
422 set_value_entry_val(lmt_node_fields_dir, 1, integer_field, dir);
423 set_value_entry_val(lmt_node_fields_dir, 2, integer_field, level);
424
425 lmt_node_fields_disc = lmt_aux_allocate_value_info( 6);
426
427 set_value_entry_val(lmt_node_fields_disc, 0, attribute_field, attr);
428 set_value_entry_val(lmt_node_fields_disc, 1, node_list_field, pre);
429 set_value_entry_val(lmt_node_fields_disc, 2, node_list_field, post);
430 set_value_entry_val(lmt_node_fields_disc, 3, node_list_field, replace);
431 set_value_entry_val(lmt_node_fields_disc, 4, integer_field, penalty);
432 set_value_entry_val(lmt_node_fields_disc, 5, integer_field, options);
433
434 lmt_node_fields_fence = lmt_aux_allocate_value_info(10);
435
436 set_value_entry_val(lmt_node_fields_fence, 0, attribute_field, attr);
437 set_value_entry_val(lmt_node_fields_fence, 1, node_list_field, delimiter);
438 set_value_entry_val(lmt_node_fields_fence, 2, dimension_field, italic);
439 set_value_entry_val(lmt_node_fields_fence, 3, dimension_field, height);
440 set_value_entry_val(lmt_node_fields_fence, 4, dimension_field, depth);
441 set_value_entry_val(lmt_node_fields_fence, 5, integer_field, options);
442 set_value_entry_val(lmt_node_fields_fence, 6, integer_field, class);
443 set_value_entry_val(lmt_node_fields_fence, 7, integer_field, source);
444 set_value_entry_val(lmt_node_fields_fence, 8, node_list_field, top);
445 set_value_entry_val(lmt_node_fields_fence, 9, node_list_field, bottom);
446
447 lmt_node_fields_fraction = lmt_aux_allocate_value_info(9);
448
449 set_value_entry_val(lmt_node_fields_fraction, 0, attribute_field, attr);
450 set_value_entry_val(lmt_node_fields_fraction, 1, dimension_field, width);
451 set_value_entry_val(lmt_node_fields_fraction, 2, node_list_field, numerator);
452 set_value_entry_val(lmt_node_fields_fraction, 3, node_list_field, denominator);
453 set_value_entry_val(lmt_node_fields_fraction, 4, node_list_field, left);
454 set_value_entry_val(lmt_node_fields_fraction, 5, node_list_field, right);
455 set_value_entry_val(lmt_node_fields_fraction, 6, node_list_field, middle);
456 set_value_entry_val(lmt_node_fields_fraction, 7, integer_field, fam);
457 set_value_entry_val(lmt_node_fields_fraction, 8, integer_field, options);
458
459 lmt_node_fields_glue = lmt_aux_allocate_value_info(9);
460
461 set_value_entry_val(lmt_node_fields_glue, 0, attribute_field, attr);
462 set_value_entry_val(lmt_node_fields_glue, 1, node_list_field, leader);
463 set_value_entry_val(lmt_node_fields_glue, 2, dimension_field, width);
464 set_value_entry_val(lmt_node_fields_glue, 3, dimension_field, stretch);
465 set_value_entry_val(lmt_node_fields_glue, 4, dimension_field, shrink);
466 set_value_entry_val(lmt_node_fields_glue, 5, integer_field, stretchorder);
467 set_value_entry_val(lmt_node_fields_glue, 6, integer_field, shrinkorder);
468 set_value_entry_val(lmt_node_fields_glue, 7, integer_field, font);
469 set_value_entry_val(lmt_node_fields_glue, 8, integer_field, options);
470
471 lmt_node_fields_glue_spec = lmt_aux_allocate_value_info(5);
472
473 set_value_entry_val(lmt_node_fields_glue_spec, 0, dimension_field, width);
474 set_value_entry_val(lmt_node_fields_glue_spec, 1, dimension_field, stretch);
475 set_value_entry_val(lmt_node_fields_glue_spec, 2, dimension_field, shrink);
476 set_value_entry_val(lmt_node_fields_glue_spec, 3, integer_field, stretchorder);
477 set_value_entry_val(lmt_node_fields_glue_spec, 4, integer_field, shrinkorder);
478
479 lmt_node_fields_glyph = lmt_aux_allocate_value_info(27);
480
481 set_value_entry_val(lmt_node_fields_glyph, 0, attribute_field, attr);
482 set_value_entry_val(lmt_node_fields_glyph, 1, integer_field, char);
483 set_value_entry_val(lmt_node_fields_glyph, 2, integer_field, font);
484 set_value_entry_val(lmt_node_fields_glyph, 3, integer_field, language);
485 set_value_entry_val(lmt_node_fields_glyph, 4, integer_field, lhmin);
486 set_value_entry_val(lmt_node_fields_glyph, 5, integer_field, rhmin);
487 set_value_entry_val(lmt_node_fields_glyph, 6, integer_field, uchyph);
488 set_value_entry_val(lmt_node_fields_glyph, 7, integer_field, state);
489 set_value_entry_val(lmt_node_fields_glyph, 8, dimension_field, left);
490 set_value_entry_val(lmt_node_fields_glyph, 9, dimension_field, right);
491 set_value_entry_val(lmt_node_fields_glyph, 10, dimension_field, xoffset);
492 set_value_entry_val(lmt_node_fields_glyph, 11, dimension_field, yoffset);
493 set_value_entry_val(lmt_node_fields_glyph, 12, dimension_field, xscale);
494 set_value_entry_val(lmt_node_fields_glyph, 13, dimension_field, yscale);
495 set_value_entry_val(lmt_node_fields_glyph, 14, dimension_field, width);
496 set_value_entry_val(lmt_node_fields_glyph, 15, dimension_field, height);
497 set_value_entry_val(lmt_node_fields_glyph, 16, dimension_field, depth);
498 set_value_entry_val(lmt_node_fields_glyph, 17, dimension_field, total);
499 set_value_entry_val(lmt_node_fields_glyph, 18, integer_field, expansion);
500 set_value_entry_val(lmt_node_fields_glyph, 19, integer_field, data);
501 set_value_entry_val(lmt_node_fields_glyph, 20, integer_field, script);
502 set_value_entry_val(lmt_node_fields_glyph, 21, integer_field, hyphenate);
503 set_value_entry_val(lmt_node_fields_glyph, 22, integer_field, options);
504 set_value_entry_val(lmt_node_fields_glyph, 23, integer_field, protected);
505 set_value_entry_val(lmt_node_fields_glyph, 24, integer_field, properties);
506 set_value_entry_val(lmt_node_fields_glyph, 25, integer_field, group);
507 set_value_entry_val(lmt_node_fields_glyph, 26, integer_field, index);
508
509 lmt_node_fields_insert = lmt_aux_allocate_value_info(6);
510
511 set_value_entry_val(lmt_node_fields_insert, 0, attribute_field, attr);
512 set_value_entry_val(lmt_node_fields_insert, 1, integer_field, cost);
513 set_value_entry_val(lmt_node_fields_insert, 2, dimension_field, depth);
514 set_value_entry_val(lmt_node_fields_insert, 3, dimension_field, height);
515 set_value_entry_val(lmt_node_fields_insert, 4, integer_field, spec);
516 set_value_entry_val(lmt_node_fields_insert, 5, node_list_field, list);
517
518 lmt_node_fields_split = lmt_aux_allocate_value_info(6);
519
520 set_value_entry_val(lmt_node_fields_split, 0, attribute_field, height);
521 set_value_entry_val(lmt_node_fields_split, 1, integer_field, index);
522 set_value_entry_val(lmt_node_fields_split, 2, node_field, lastinsert);
523 set_value_entry_val(lmt_node_fields_split, 3, node_field, bestinsert);
524 set_value_entry_val(lmt_node_fields_split, 4, integer_field, stretchorder);
525 set_value_entry_val(lmt_node_fields_split, 5, integer_field, shrinkorder);
526
527 lmt_node_fields_kern = lmt_aux_allocate_value_info(3);
528
529 set_value_entry_val(lmt_node_fields_kern, 0, attribute_field, attr);
530 set_value_entry_val(lmt_node_fields_kern, 1, dimension_field, kern);
531 set_value_entry_val(lmt_node_fields_kern, 2, integer_field, expansion);
532
533 lmt_node_fields_list = lmt_aux_allocate_value_info(20);
534
535 set_value_entry_val(lmt_node_fields_list, 0, attribute_field, attr);
536 set_value_entry_val(lmt_node_fields_list, 1, dimension_field, width);
537 set_value_entry_val(lmt_node_fields_list, 2, dimension_field, depth);
538 set_value_entry_val(lmt_node_fields_list, 3, dimension_field, height);
539 set_value_entry_val(lmt_node_fields_list, 4, integer_field, direction);
540 set_value_entry_val(lmt_node_fields_list, 5, dimension_field, shift);
541 set_value_entry_val(lmt_node_fields_list, 6, integer_field, glueorder);
542 set_value_entry_val(lmt_node_fields_list, 7, integer_field, gluesign);
543 set_value_entry_val(lmt_node_fields_list, 8, integer_field, glueset);
544 set_value_entry_val(lmt_node_fields_list, 9, node_list_field, list);
545 set_value_entry_val(lmt_node_fields_list, 10, integer_field, orientation);
546 set_value_entry_val(lmt_node_fields_list, 11, integer_field, source);
547 set_value_entry_val(lmt_node_fields_list, 12, integer_field, target);
548 set_value_entry_val(lmt_node_fields_list, 13, dimension_field, woffset);
549 set_value_entry_val(lmt_node_fields_list, 14, dimension_field, hoffset);
550 set_value_entry_val(lmt_node_fields_list, 15, dimension_field, doffset);
551 set_value_entry_val(lmt_node_fields_list, 16, dimension_field, xoffset);
552 set_value_entry_val(lmt_node_fields_list, 17, dimension_field, yoffset);
553 set_value_entry_val(lmt_node_fields_list, 18, integer_field, state);
554 set_value_entry_val(lmt_node_fields_list, 19, integer_field, class);
555
556 lmt_node_fields_par = lmt_aux_allocate_value_info(9);
557 set_value_entry_val(lmt_node_fields_par, 0, attribute_field, attr);
558 set_value_entry_val(lmt_node_fields_par, 1, integer_field, interlinepenalty);
559 set_value_entry_val(lmt_node_fields_par, 2, integer_field, brokenpenalty);
560 set_value_entry_val(lmt_node_fields_par, 3, integer_field, dir);
561 set_value_entry_val(lmt_node_fields_par, 4, node_field, leftbox);
562 set_value_entry_val(lmt_node_fields_par, 5, dimension_field, leftboxwidth);
563 set_value_entry_val(lmt_node_fields_par, 6, node_field, rightbox);
564 set_value_entry_val(lmt_node_fields_par, 7, dimension_field, rightboxwidth);
565 set_value_entry_val(lmt_node_fields_par, 8, node_field, middlebox);
566
567 lmt_node_fields_mark = lmt_aux_allocate_value_info(3);
568
569 set_value_entry_val(lmt_node_fields_mark, 0, attribute_field, attr);
570 set_value_entry_val(lmt_node_fields_mark, 1, integer_field, class);
571 set_value_entry_val(lmt_node_fields_mark, 2, token_list_field, mark);
572
573 lmt_node_fields_math = lmt_aux_allocate_value_info(9);
574
575 set_value_entry_val(lmt_node_fields_math, 0, attribute_field, attr);
576 set_value_entry_val(lmt_node_fields_math, 1, integer_field, surround);
577 set_value_entry_val(lmt_node_fields_math, 2, dimension_field, width);
578 set_value_entry_val(lmt_node_fields_math, 3, dimension_field, stretch);
579 set_value_entry_val(lmt_node_fields_math, 4, dimension_field, shrink);
580 set_value_entry_val(lmt_node_fields_math, 5, integer_field, stretchorder);
581 set_value_entry_val(lmt_node_fields_math, 6, integer_field, shrinkorder);
582 set_value_entry_val(lmt_node_fields_math, 7, integer_field, penalty);
583 set_value_entry_val(lmt_node_fields_glue, 8, integer_field, options);
584
585 lmt_node_fields_math_char = lmt_aux_allocate_value_info(7);
586
587 set_value_entry_val(lmt_node_fields_math_char, 0, attribute_field, attr);
588 set_value_entry_val(lmt_node_fields_math_char, 1, integer_field, fam);
589 set_value_entry_val(lmt_node_fields_math_char, 2, integer_field, char);
590 set_value_entry_val(lmt_node_fields_math_char, 3, integer_field, options);
591 set_value_entry_val(lmt_node_fields_math_char, 4, integer_field, properties);
592 set_value_entry_val(lmt_node_fields_math_char, 5, integer_field, group);
593 set_value_entry_val(lmt_node_fields_math_char, 6, integer_field, index);
594
595 lmt_node_fields_math_text_char = lmt_aux_allocate_value_info(4);
596
597 set_value_entry_val(lmt_node_fields_math_text_char, 0, attribute_field, attr);
598 set_value_entry_val(lmt_node_fields_math_text_char, 1, integer_field, fam);
599 set_value_entry_val(lmt_node_fields_math_text_char, 2, integer_field, char);
600 set_value_entry_val(lmt_node_fields_math_text_char, 3, integer_field, options);
601
602 lmt_node_fields_noad = lmt_aux_allocate_value_info(8);
603
604 set_value_entry_val(lmt_node_fields_noad, 0, attribute_field, attr);
605 set_value_entry_val(lmt_node_fields_noad, 1, node_list_field, nucleus);
606 set_value_entry_val(lmt_node_fields_noad, 2, node_list_field, sub);
607 set_value_entry_val(lmt_node_fields_noad, 3, node_list_field, sup);
608 set_value_entry_val(lmt_node_fields_noad, 4, node_list_field, subpre);
609 set_value_entry_val(lmt_node_fields_noad, 5, node_list_field, suppre);
610 set_value_entry_val(lmt_node_fields_noad, 6, node_list_field, prime);
611 set_value_entry_val(lmt_node_fields_noad, 7, integer_field, options);
612
613 lmt_node_fields_penalty = lmt_aux_allocate_value_info(2);
614
615 set_value_entry_val(lmt_node_fields_penalty, 0, attribute_field, attr);
616 set_value_entry_val(lmt_node_fields_penalty, 1, integer_field, penalty);
617
618 lmt_node_fields_radical = lmt_aux_allocate_value_info(11);
619
620 set_value_entry_val(lmt_node_fields_radical, 0, attribute_field, attr);
621 set_value_entry_val(lmt_node_fields_radical, 1, node_list_field, nucleus);
622 set_value_entry_val(lmt_node_fields_radical, 2, node_list_field, sub);
623 set_value_entry_val(lmt_node_fields_radical, 3, node_list_field, sup);
624 set_value_entry_val(lmt_node_fields_radical, 4, node_list_field, presub);
625 set_value_entry_val(lmt_node_fields_radical, 5, node_list_field, presup);
626 set_value_entry_val(lmt_node_fields_radical, 6, node_list_field, prime);
627 set_value_entry_val(lmt_node_fields_radical, 7, node_list_field, left);
628 set_value_entry_val(lmt_node_fields_radical, 8, node_list_field, degree);
629 set_value_entry_val(lmt_node_fields_radical, 9, dimension_field, width);
630 set_value_entry_val(lmt_node_fields_radical, 10, integer_field, options);
631
632 lmt_node_fields_rule = lmt_aux_allocate_value_info(11);
633
634 set_value_entry_val(lmt_node_fields_rule, 0, attribute_field, attr);
635 set_value_entry_val(lmt_node_fields_rule, 1, dimension_field, width);
636 set_value_entry_val(lmt_node_fields_rule, 2, dimension_field, depth);
637 set_value_entry_val(lmt_node_fields_rule, 3, dimension_field, height);
638 set_value_entry_val(lmt_node_fields_rule, 4, dimension_field, xoffset);
639 set_value_entry_val(lmt_node_fields_rule, 5, dimension_field, yoffset);
640 set_value_entry_val(lmt_node_fields_rule, 6, dimension_field, left);
641 set_value_entry_val(lmt_node_fields_rule, 7, dimension_field, right);
642 set_value_entry_val(lmt_node_fields_rule, 8, integer_field, data);
643 set_value_entry_val(lmt_node_fields_rule, 9, integer_field, char);
644 set_value_entry_val(lmt_node_fields_rule, 10, integer_field, font);
645
646 lmt_node_fields_style = lmt_aux_allocate_value_info(2);
647
648 set_value_entry_val(lmt_node_fields_style, 0, attribute_field, attr);
649 set_value_entry_val(lmt_node_fields_style, 1, integer_field, style);
650
651 lmt_node_fields_parameter = lmt_aux_allocate_value_info(4);
652
653 set_value_entry_val(lmt_node_fields_parameter, 0, integer_field, style);
654 set_value_entry_val(lmt_node_fields_parameter, 1, integer_field, name);
655 set_value_entry_val(lmt_node_fields_parameter, 2, integer_field, value);
656 set_value_entry_val(lmt_node_fields_parameter, 3, node_list_field, list);
657
658 lmt_node_fields_sub_box = lmt_aux_allocate_value_info(2);
659
660 set_value_entry_val(lmt_node_fields_sub_box, 0, attribute_field, attr);
661 set_value_entry_val(lmt_node_fields_sub_box, 1, node_list_field, list);
662
663 lmt_node_fields_sub_mlist = lmt_aux_allocate_value_info(2);
664
665 set_value_entry_val(lmt_node_fields_sub_mlist, 0, attribute_field, attr);
666 set_value_entry_val(lmt_node_fields_sub_mlist, 1, node_list_field, list);
667
668 lmt_node_fields_unset = lmt_aux_allocate_value_info(11);
669
670 set_value_entry_val(lmt_node_fields_unset, 0, attribute_field, attr);
671 set_value_entry_val(lmt_node_fields_unset, 1, dimension_field, width);
672 set_value_entry_val(lmt_node_fields_unset, 2, dimension_field, depth);
673 set_value_entry_val(lmt_node_fields_unset, 3, dimension_field, height);
674 set_value_entry_val(lmt_node_fields_unset, 4, integer_field, dir);
675 set_value_entry_val(lmt_node_fields_unset, 5, dimension_field, shrink);
676 set_value_entry_val(lmt_node_fields_unset, 6, integer_field, glueorder);
677 set_value_entry_val(lmt_node_fields_unset, 7, integer_field, gluesign);
678 set_value_entry_val(lmt_node_fields_unset, 8, dimension_field, stretch);
679 set_value_entry_val(lmt_node_fields_unset, 9, integer_field, span);
680 set_value_entry_val(lmt_node_fields_unset, 10, node_list_field, list);
681
682 lmt_node_fields_whatsit = lmt_aux_allocate_value_info(1);
683
684 set_value_entry_val(lmt_node_fields_whatsit, 0, attribute_field, attr);
685
686 lmt_interface.node_data = lmt_memory_malloc((passive_node + 2) * sizeof(node_info));
687
688
698
699 lmt_interface.node_data[hlist_node] = (node_info) { .id = hlist_node, .size = box_node_size, .first = 0, .last = last_list_subtype, .subtypes = subtypes_list, .fields = lmt_node_fields_list, .name = lua_key(hlist), .lua = lua_key_index(hlist), .visible = 1 };
700 lmt_interface.node_data[vlist_node] = (node_info) { .id = vlist_node, .size = box_node_size, .first = 0, .last = last_list_subtype, .subtypes = subtypes_list, .fields = lmt_node_fields_list, .name = lua_key(vlist), .lua = lua_key_index(vlist), .visible = 1 };
701 lmt_interface.node_data[rule_node] = (node_info) { .id = rule_node, .size = rule_node_size, .first = 0, .last = last_rule_subtype, .subtypes = subtypes_rule, .fields = lmt_node_fields_rule, .name = lua_key(rule), .lua = lua_key_index(rule), .visible = 1 };
702 lmt_interface.node_data[insert_node] = (node_info) { .id = insert_node, .size = insert_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_insert, .name = lua_key(insert), .lua = lua_key_index(insert), .visible = 1 };
703 lmt_interface.node_data[mark_node] = (node_info) { .id = mark_node, .size = mark_node_size, .first = 0, .last = last_mark_subtype, .subtypes = subtypes_mark, .fields = lmt_node_fields_mark, .name = lua_key(mark), .lua = lua_key_index(mark), .visible = 1 };
704 lmt_interface.node_data[adjust_node] = (node_info) { .id = adjust_node, .size = adjust_node_size, .first = 0, .last = last_adjust_subtype, .subtypes = subtypes_adjust, .fields = lmt_node_fields_adjust, .name = lua_key(adjust), .lua = lua_key_index(adjust), .visible = 1 };
705 lmt_interface.node_data[boundary_node] = (node_info) { .id = boundary_node, .size = boundary_node_size, .first = 0, .last = last_boundary_subtype, .subtypes = subtypes_boundary, .fields = lmt_node_fields_boundary, .name = lua_key(boundary), .lua = lua_key_index(boundary), .visible = 1 };
706 lmt_interface.node_data[disc_node] = (node_info) { .id = disc_node, .size = disc_node_size, .first = 0, .last = last_discretionary_subtype, .subtypes = subtypes_disc, .fields = lmt_node_fields_disc, .name = lua_key(disc), .lua = lua_key_index(disc), .visible = 1 };
707 lmt_interface.node_data[whatsit_node] = (node_info) { .id = whatsit_node, .size = whatsit_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_whatsit, .name = lua_key(whatsit), .lua = lua_key_index(whatsit), .visible = 1 };
708 lmt_interface.node_data[par_node] = (node_info) { .id = par_node, .size = par_node_size, .first = 0, .last = last_par_subtype, .subtypes = subtypes_par, .fields = lmt_node_fields_par, .name = lua_key(par), .lua = lua_key_index(par), .visible = 1 };
709 lmt_interface.node_data[dir_node] = (node_info) { .id = dir_node, .size = dir_node_size, .first = 0, .last = last_dir_subtype, .subtypes = subtypes_dir, .fields = lmt_node_fields_dir, .name = lua_key(dir), .lua = lua_key_index(dir), .visible = 1 };
710 lmt_interface.node_data[math_node] = (node_info) { .id = math_node, .size = math_node_size, .first = 0, .last = last_math_subtype, .subtypes = subtypes_math, .fields = lmt_node_fields_math, .name = lua_key(math), .lua = lua_key_index(math), .visible = 1 };
711 lmt_interface.node_data[glue_node] = (node_info) { .id = glue_node, .size = glue_node_size, .first = 0, .last = last_glue_subtype, .subtypes = subtypes_glue, .fields = lmt_node_fields_glue, .name = lua_key(glue), .lua = lua_key_index(glue), .visible = 1 };
712 lmt_interface.node_data[kern_node] = (node_info) { .id = kern_node, .size = kern_node_size, .first = 0, .last = last_kern_subtype, .subtypes = subtypes_kern, .fields = lmt_node_fields_kern, .name = lua_key(kern), .lua = lua_key_index(kern), .visible = 1 };
713 lmt_interface.node_data[penalty_node] = (node_info) { .id = penalty_node, .size = penalty_node_size, .first = 0, .last = last_penalty_subtype, .subtypes = subtypes_penalty, .fields = lmt_node_fields_penalty, .name = lua_key(penalty), .lua = lua_key_index(penalty), .visible = 1 };
714 lmt_interface.node_data[style_node] = (node_info) { .id = style_node, .size = style_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_style, .name = lua_key(style), .lua = lua_key_index(style), .visible = 1 };
715 lmt_interface.node_data[choice_node] = (node_info) { .id = choice_node, .size = choice_node_size, .first = 0, .last = last_choice_subtype, .subtypes = subtypes_choice, .fields = lmt_node_fields_choice, .name = lua_key(choice), .lua = lua_key_index(choice), .visible = 1 };
716 lmt_interface.node_data[parameter_node] = (node_info) { .id = parameter_node, .size = parameter_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_parameter, .name = lua_key(parameter), .lua = lua_key_index(parameter), .visible = 1 };
717 lmt_interface.node_data[simple_noad] = (node_info) { .id = simple_noad, .size = noad_size, .first = 0, .last = last_noad_subtype, .subtypes = subtypes_noad, .fields = lmt_node_fields_noad, .name = lua_key(noad), .lua = lua_key_index(noad), .visible = 1 };
718 lmt_interface.node_data[radical_noad] = (node_info) { .id = radical_noad, .size = radical_noad_size, .first = 0, .last = last_radical_subtype, .subtypes = subtypes_radical, .fields = lmt_node_fields_radical, .name = lua_key(radical), .lua = lua_key_index(radical), .visible = 1 };
719 lmt_interface.node_data[fraction_noad] = (node_info) { .id = fraction_noad, .size = fraction_noad_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_fraction, .name = lua_key(fraction), .lua = lua_key_index(fraction), .visible = 1 };
720 lmt_interface.node_data[accent_noad] = (node_info) { .id = accent_noad, .size = accent_noad_size, .first = 0, .last = last_accent_subtype, .subtypes = subtypes_accent, .fields = lmt_node_fields_accent, .name = lua_key(accent), .lua = lua_key_index(accent), .visible = 1 };
721 lmt_interface.node_data[fence_noad] = (node_info) { .id = fence_noad, .size = fence_noad_size, .first = 0, .last = last_fence_subtype, .subtypes = subtypes_fence, .fields = lmt_node_fields_fence, .name = lua_key(fence), .lua = lua_key_index(fence), .visible = 1 };
722 lmt_interface.node_data[math_char_node] = (node_info) { .id = math_char_node, .size = math_kernel_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_math_char, .name = lua_key(mathchar), .lua = lua_key_index(mathchar), .visible = 1 };
723 lmt_interface.node_data[math_text_char_node] = (node_info) { .id = math_text_char_node, .size = math_kernel_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_math_text_char, .name = lua_key(mathtextchar), .lua = lua_key_index(mathtextchar), .visible = 1 };
724 lmt_interface.node_data[sub_box_node] = (node_info) { .id = sub_box_node, .size = math_kernel_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_sub_box, .name = lua_key(subbox), .lua = lua_key_index(subbox), .visible = 1 };
725 lmt_interface.node_data[sub_mlist_node] = (node_info) { .id = sub_mlist_node, .size = math_kernel_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_sub_mlist, .name = lua_key(submlist), .lua = lua_key_index(submlist), .visible = 1 };
726 lmt_interface.node_data[delimiter_node] = (node_info) { .id = delimiter_node, .size = math_delimiter_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_delimiter, .name = lua_key(delimiter), .lua = lua_key_index(delimiter), .visible = 1 };
727 lmt_interface.node_data[glyph_node] = (node_info) { .id = glyph_node, .size = glyph_node_size, .first = 0, .last = last_glyph_subtype, .subtypes = subtypes_glyph, .fields = lmt_node_fields_glyph, .name = lua_key(glyph), .lua = lua_key_index(glyph), .visible = 1 };
728
729
732
733 lmt_interface.node_data[unset_node] = (node_info) { .id = unset_node, .size = box_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_unset, .name = lua_key(unset), .lua = lua_key_index(unset), .visible = 1 };
734 lmt_interface.node_data[specification_node] = (node_info) { .id = specification_node, .size = specification_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(specification), .lua = lua_key_index(specification), .visible = 0 };
735 lmt_interface.node_data[align_record_node] = (node_info) { .id = align_record_node, .size = box_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_unset, .name = lua_key(alignrecord), .lua = lua_key_index(alignrecord), .visible = 1 };
736
737
741
742 lmt_interface.node_data[attribute_node] = (node_info) { .id = attribute_node, .size = attribute_node_size, .first = 0, .last = last_attribute_subtype, .subtypes = subtypes_attribute,.fields = lmt_node_fields_attribute, .name = lua_key(attribute), .lua = lua_key_index(attribute), .visible = 1 };
743
744
748
749 lmt_interface.node_data[glue_spec_node] = (node_info) { .id = glue_spec_node, .size = glue_spec_size, .first = 0, .last = 0, .subtypes = NULL, .fields = lmt_node_fields_glue_spec, .name = lua_key(gluespec), .lua = lua_key_index(gluespec), .visible = 1 };
750
751
755
756 lmt_interface.node_data[temp_node] = (node_info) { .id = temp_node, .size = temp_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(temp), .lua = lua_key_index(temp), .visible = 1 };
757
758
761
762 lmt_interface.node_data[split_node] = (node_info) { .id = split_node, .size = split_node_size, .first = 0, .last = last_split_subtype, .subtypes = subtypes_split, .fields = lmt_node_fields_split, .name = lua_key(split), .lua = lua_key_index(split), .visible = 1 };
763
764
769
770 lmt_interface.node_data[expression_node] = (node_info) { .id = expression_node, .size = expression_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(expression), .lua = lua_key_index(expression), .visible = 0 };
771 lmt_interface.node_data[loop_state_node] = (node_info) { .id = loop_state_node, .size = loop_state_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(loopstate), .lua = lua_key_index(loopstate), .visible = 0 };
772 lmt_interface.node_data[math_spec_node] = (node_info) { .id = math_spec_node, .size = math_spec_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(mathspec), .lua = lua_key_index(mathspec), .visible = 0 };
773 lmt_interface.node_data[font_spec_node] = (node_info) { .id = font_spec_node, .size = font_spec_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(fontspec), .lua = lua_key_index(fontspec), .visible = 0 };
774 lmt_interface.node_data[nesting_node] = (node_info) { .id = nesting_node, .size = nesting_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(nestedlist), .lua = lua_key_index(nestedlist), .visible = 0 };
775 lmt_interface.node_data[span_node] = (node_info) { .id = span_node, .size = span_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(span), .lua = lua_key_index(span), .visible = 0 };
776 lmt_interface.node_data[align_stack_node] = (node_info) { .id = align_stack_node, .size = align_stack_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(alignstack), .lua = lua_key_index(alignstack), .visible = 0 };
777
778 lmt_interface.node_data[if_node] = (node_info) { .id = if_node, .size = if_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(ifstack), .lua = lua_key_index(ifstack), .visible = 0 };
779 lmt_interface.node_data[unhyphenated_node] = (node_info) { .id = unhyphenated_node, .size = active_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(unhyphenated), .lua = lua_key_index(unhyphenated), .visible = 0 };
780 lmt_interface.node_data[hyphenated_node] = (node_info) { .id = hyphenated_node, .size = active_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(hyphenated), .lua = lua_key_index(hyphenated), .visible = 0 };
781 lmt_interface.node_data[delta_node] = (node_info) { .id = delta_node, .size = delta_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(delta), .lua = lua_key_index(delta), .visible = 0 };
782 lmt_interface.node_data[passive_node] = (node_info) { .id = passive_node, .size = passive_node_size, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = lua_key(passive), .lua = lua_key_index(passive), .visible = 0 };
783 lmt_interface.node_data[passive_node + 1] = (node_info) { .id = -1, .size = -1, .first = 0, .last = 0, .subtypes = NULL, .fields = NULL, .name = NULL, .lua = 0, .visible = 0 };
784
785}
786
787
842
843inline static void lmt_properties_push(lua_State * L)
844{
845 lmt_node_memory_state.lua_properties_level++;
846 if (lmt_node_memory_state.lua_properties_level == 1) {
847 lua_rawgeti(L, LUA_REGISTRYINDEX, lmt_node_memory_state.node_properties_id);
848 }
849}
850
851inline static void lmt_properties_pop(lua_State * L)
852{
853 if (lmt_node_memory_state.lua_properties_level == 1) {
854 lua_pop(L, 1);
855 }
856 lmt_node_memory_state.lua_properties_level--;
857}
858
859
860
861inline static void lmt_properties_reset(lua_State * L, halfword target)
862{
863 if (lmt_node_memory_state.lua_properties_level == 0) {
864 lua_rawgeti(L, LUA_REGISTRYINDEX, lmt_node_memory_state.node_properties_id);
865 lua_pushnil(L);
866 lua_rawseti(L, -2, target);
867 lua_pop(L, 1);
868 } else {
869 lua_pushnil(L);
870 lua_rawseti(L, -2, target);
871 }
872}
873
874inline static void lmt_properties_copy(lua_State *L, halfword target, halfword source)
875{
876 if (lmt_node_memory_state.lua_properties_level == 0) {
877 lua_rawgeti(L, LUA_REGISTRYINDEX, lmt_node_memory_state.node_properties_id);
878 }
879
880 if (lua_rawgeti(L, -1, source) == LUA_TTABLE) {
881
882 lua_createtable(L, 0, 1);
883
884 lua_insert(L, -2);
885
886 lua_push_key(__index);
887
888 lua_insert(L, -2);
889
890 lua_rawset(L, -3);
891
892 lua_createtable(L, 0, 1);
893
894 lua_insert(L, -2);
895
896 lua_setmetatable(L, -2);
897
898 lua_rawseti(L, -2, target);
899
900 } else {
901
902 lua_pop(L, 1);
903 }
904
905 if (lmt_node_memory_state.lua_properties_level == 0) {
906 lua_pop(L, 1);
907 }
908}
909
910
911
912void tex_reset_node_properties(halfword b)
913{
914 if (b) {
915 lmt_properties_reset(lmt_lua_state.lua_instance, b);
916 }
917}
918
919
920
921static void tex_aux_node_range_test(halfword a, halfword b)
922{
923 if (b < 0 || b >= lmt_node_memory_state.nodes_data.allocated) {
924 tex_formatted_error("nodes", "node range test failed in %s node", lmt_interface.node_data[node_type(a)].name);
925 }
926}
927
928
941
942
943
944
945
946inline static void tex_aux_preset_disc_node(halfword n)
947{
948 disc_pre_break(n) = disc_pre_break_node(n);
949 disc_post_break(n) = disc_post_break_node(n);
950 disc_no_break(n) = disc_no_break_node(n);
951 node_type(disc_pre_break(n)) = nesting_node;
952 node_type(disc_post_break(n)) = nesting_node;
953 node_type(disc_no_break(n)) = nesting_node;
954 node_subtype(disc_pre_break(n)) = pre_break_code;
955 node_subtype(disc_post_break(n)) = post_break_code;
956 node_subtype(disc_no_break(n)) = no_break_code;
957}
958
959inline static void tex_aux_preset_node(halfword n, quarterword type)
960{
961 switch (type) {
962 case glyph_node:
963 break;
964 case hlist_node:
965 case vlist_node:
966 box_dir(n) = direction_unknown;
967 break;
968 case disc_node:
969 tex_aux_preset_disc_node(n);
970 break;
971 case rule_node:
972 rule_width(n) = null_flag;
973 rule_depth(n) = null_flag;
974 rule_height(n) = null_flag;
975 rule_data(n) = 0;
976 break;
977 case unset_node:
978 box_width(n) = null_flag;
979 break;
980 case specification_node:
981 tex_null_specification_list(n);
982 break;
983 case simple_noad:
984 case radical_noad:
985 case fraction_noad:
986 case accent_noad:
987 case fence_noad:
988 noad_family(n) = unused_math_family;
989 noad_style(n) = unused_math_style;
990 reset_noad_classes(n);
991 break;
992 }
993}
994
995halfword tex_new_node(quarterword type, quarterword subtype)
996{
997 halfword size = get_node_size(type);
998 halfword node = tex_get_node(size);
999
1000
1006
1007 memset((void *) (lmt_node_memory_state.nodes + node + 1), 0, (sizeof(memoryword) * ((size_t) size - 1)));
1008
1009 if (tex_nodetype_is_complex(type)) {
1010 tex_aux_preset_node(node, type);
1011 if (input_file_state.mode > 0) {
1012
1013 switch (type) {
1014 case glyph_node:
1015 if (input_file_state.mode > 1) {
1016 glyph_input_file(node) = input_file_value();
1017 glyph_input_line(node) = input_line_value();
1018 }
1019 break;
1020 case hlist_node:
1021 case vlist_node:
1022 case unset_node:
1023 box_input_file(node) = input_file_value();
1024 box_input_line(node) = input_line_value();
1025 break;
1026 }
1027 }
1028 if (tex_nodetype_has_attributes(type)) {
1029 attach_current_attribute_list(node);
1030 }
1031 }
1032
1033 node_type(node) = type;
1034 node_subtype(node) = subtype;
1035 return node;
1036}
1037
1038halfword tex_new_temp_node(void)
1039{
1040 halfword n = tex_get_node(temp_node_size);
1041 node_type(n) = temp_node;
1042 node_subtype(n) = 0;
1043 memset((void *) (lmt_node_memory_state.nodes + n + 1), 0, (sizeof(memoryword) * (temp_node_size - 1)));
1044 return n;
1045}
1046
1047static halfword tex_aux_new_glyph_node_with_attributes(halfword parent)
1048{
1049 halfword n = tex_get_node(glyph_node_size);
1050 memset((void *) (lmt_node_memory_state.nodes + n + 1), 0, (sizeof(memoryword) * (glyph_node_size - 1)));
1051 if (input_file_state.mode > 1) {
1052 glyph_input_file(n) = input_file_value();
1053 glyph_input_line(n) = input_line_value();
1054 }
1055 node_type(n) = glyph_node;
1056 node_subtype(n) = glyph_unset_subtype;
1057 if (parent) {
1058 tex_attach_attribute_list_copy(n, parent);
1059 } else {
1060 attach_current_attribute_list(n);
1061 }
1062 return n;
1063}
1064
1065
1069
1070halfword tex_copy_node_list(halfword p, halfword end)
1071{
1072
1073 halfword h = null;
1074
1075 halfword q = null;
1076
1077 lua_State *L = lmt_lua_state.lua_instance;
1078 lmt_properties_push(L);
1079 while (p != end) {
1080 halfword s = tex_copy_node(p);
1081 if (h) {
1082 tex_couple_nodes(q, s);
1083 } else {
1084 h = s;
1085 }
1086 q = s;
1087 p = node_next(p);
1088 }
1089
1090 lmt_properties_pop(L);
1091 return h;
1092}
1093
1094
1095
1096halfword tex_copy_node_only(halfword p)
1097{
1098 quarterword t = node_type(p);
1099 int s = get_node_size(t);
1100 halfword r = tex_get_node(s);
1101 memcpy((void *) (lmt_node_memory_state.nodes + r), (void *) (lmt_node_memory_state.nodes + p), (sizeof(memoryword) ));
1102 memset((void *) (lmt_node_memory_state.nodes + r + 1), 0, (sizeof(memoryword) * ((unsigned) s - 1)));
1103 tex_aux_preset_node(r, t);
1104 return r;
1105}
1106
1107
1113
1114# define copy_sub_list(target,source) do { \
1115 if (source) { \
1116 halfword copy_stub = tex_copy_node_list(source, null); \
1117 target = copy_stub; \
1118 } else { \
1119 target = null; \
1120 } \
1121 } while (0)
1122
1123# define copy_sub_node(target,source) do { \
1124 if (source) { \
1125 halfword copy_stub = tex_copy_node(source); \
1126 target = copy_stub; \
1127 } else { \
1128 target = null; \
1129 } \
1130} while (0)
1131
1132
1137
1138halfword tex_copy_node(halfword original)
1139{
1140
1143 if (original < 0 || original >= lmt_node_memory_state.nodes_data.allocated) {
1144 return tex_formatted_error("nodes", "attempt to copy an impossible node %d", (int) original);
1145 } else if (original > lmt_node_memory_state.reserved && lmt_node_memory_state.nodesizes[original] == 0) {
1146 return tex_formatted_error("nodes", "attempt to copy a free %s node %d", get_node_name(node_type(original)), (int) original);
1147 } else {
1148
1149 halfword type = node_type(original);
1150 int size = get_node_size(type);
1151
1152 halfword copy = tex_get_node(size);
1153
1154 memcpy((void *) (lmt_node_memory_state.nodes + copy), (void *) (lmt_node_memory_state.nodes + original), (sizeof(memoryword) * (unsigned) size));
1155 if (tex_nodetype_is_complex(size)) {
1156 if (tex_nodetype_has_attributes(type)) {
1157 add_attribute_reference(node_attr(original));
1158 node_prev(copy) = null;
1159 lmt_properties_copy(lmt_lua_state.lua_instance, copy, original);
1160 }
1161 node_next(copy) = null;
1162 switch (type) {
1163 case glue_node:
1164 copy_sub_list(glue_leader_ptr(copy), glue_leader_ptr(original));
1165 break;
1166 case hlist_node:
1167 copy_sub_list(box_pre_adjusted(copy), box_pre_adjusted(original));
1168 copy_sub_list(box_post_adjusted(copy), box_post_adjusted(original));
1169
1170 case vlist_node:
1171 copy_sub_list(box_pre_migrated(copy), box_pre_migrated(original));
1172 copy_sub_list(box_post_migrated(copy), box_post_migrated(original));
1173
1174 case unset_node:
1175 copy_sub_list(box_list(copy), box_list(original));
1176 break;
1177 case disc_node:
1178 disc_pre_break(copy) = disc_pre_break_node(copy);
1179 if (disc_pre_break_head(original)) {
1180 tex_set_disc_field(copy, pre_break_code, tex_copy_node_list(disc_pre_break_head(original), null));
1181 } else {
1182 tex_set_disc_field(copy, pre_break_code, null);
1183 }
1184 disc_post_break(copy) = disc_post_break_node(copy);
1185 if (disc_post_break_head(original)) {
1186 tex_set_disc_field(copy, post_break_code, tex_copy_node_list(disc_post_break_head(original), null));
1187 } else {
1188 tex_set_disc_field(copy, post_break_code, null);
1189 }
1190 disc_no_break(copy) = disc_no_break_node(copy);
1191 if (disc_no_break_head(original)) {
1192 tex_set_disc_field(copy, no_break_code, tex_copy_node_list(disc_no_break_head(original), null));
1193 } else {
1194 tex_set_disc_field(copy, no_break_code, null);
1195 }
1196 break;
1197 case insert_node:
1198 copy_sub_list(insert_list(copy), insert_list(original));
1199 break;
1200 case mark_node:
1201 tex_add_token_reference(mark_ptr(original));
1202 break;
1203 case adjust_node:
1204 copy_sub_list(adjust_list(copy), adjust_list(original));
1205 break;
1206 case choice_node:
1207 copy_sub_list(choice_display_mlist(copy), choice_display_mlist(original));
1208 copy_sub_list(choice_text_mlist(copy), choice_text_mlist(original));
1209 copy_sub_list(choice_script_mlist(copy), choice_script_mlist(original));
1210 copy_sub_list(choice_script_script_mlist(copy), choice_script_script_mlist(original));
1211 break;
1212 case simple_noad:
1213 case radical_noad:
1214 case fraction_noad:
1215 case accent_noad:
1216 copy_sub_list(noad_nucleus(copy), noad_nucleus(original));
1217 copy_sub_list(noad_subscr(copy), noad_subscr(original));
1218 copy_sub_list(noad_supscr(copy), noad_supscr(original));
1219 copy_sub_list(noad_subprescr(copy), noad_subprescr(original));
1220 copy_sub_list(noad_supprescr(copy), noad_supprescr(original));
1221 copy_sub_list(noad_prime(copy), noad_prime(original));
1222
1223 switch (type) {
1224 case radical_noad:
1225 copy_sub_node(radical_left_delimiter(copy), radical_left_delimiter(original));
1226 copy_sub_node(radical_right_delimiter(copy), radical_right_delimiter(original));
1227 copy_sub_node(radical_top_delimiter(copy), radical_top_delimiter(original));
1228 copy_sub_node(radical_bottom_delimiter(copy), radical_bottom_delimiter(original));
1229 copy_sub_list(radical_degree(copy), radical_degree(original));
1230 break;
1231 case fraction_noad:
1232
1233
1234 copy_sub_node(fraction_left_delimiter(copy), fraction_left_delimiter(original));
1235 copy_sub_node(fraction_right_delimiter(copy), fraction_right_delimiter(original));
1236 copy_sub_node(fraction_middle_delimiter(copy), fraction_middle_delimiter(original));
1237 break;
1238 case accent_noad:
1239 copy_sub_list(accent_top_character(copy), accent_top_character(original));
1240 copy_sub_list(accent_bottom_character(copy), accent_bottom_character(original));
1241 copy_sub_list(accent_middle_character(copy), accent_middle_character(original));
1242 break;
1243 }
1244 break;
1245 case fence_noad:
1246
1247 copy_sub_node(fence_delimiter_list(copy), fence_delimiter_list(original));
1248 copy_sub_node(fence_delimiter_top(copy), fence_delimiter_top(original));
1249 copy_sub_node(fence_delimiter_bottom(copy), fence_delimiter_bottom(original));
1250 break;
1251 case sub_box_node:
1252 case sub_mlist_node:
1253 copy_sub_list(kernel_math_list(copy), kernel_math_list(original));
1254 break;
1255 case par_node:
1256
1257 copy_sub_list(par_box_left(copy), par_box_left(original));
1258 copy_sub_list(par_box_right(copy), par_box_right(original));
1259 copy_sub_list(par_box_middle(copy), par_box_middle(original));
1260
1261 par_left_skip(copy) = null;
1262 par_right_skip(copy) = null;
1263 par_par_fill_left_skip(copy) = null;
1264 par_par_fill_right_skip(copy) = null;
1265 par_par_init_left_skip(copy) = null;
1266 par_par_init_right_skip(copy) = null;
1267 par_emergency_left_skip(copy) = null;
1268 par_emergency_right_skip(copy) = null;
1269 par_baseline_skip(copy) = null;
1270 par_line_skip(copy) = null;
1271 par_par_shape(copy) = null;
1272 par_inter_line_penalties(copy) = null;
1273 par_club_penalties(copy) = null;
1274 par_widow_penalties(copy) = null;
1275 par_display_widow_penalties(copy) = null;
1276 par_orphan_penalties(copy) = null;
1277 par_par_passes(copy) = null;
1278
1279 tex_set_par_par(copy, par_left_skip_code, tex_get_par_par(original, par_left_skip_code), 1);
1280 tex_set_par_par(copy, par_right_skip_code, tex_get_par_par(original, par_right_skip_code), 1);
1281 tex_set_par_par(copy, par_par_fill_left_skip_code, tex_get_par_par(original, par_par_fill_left_skip_code), 1);
1282 tex_set_par_par(copy, par_par_fill_right_skip_code, tex_get_par_par(original, par_par_fill_right_skip_code), 1);
1283 tex_set_par_par(copy, par_par_init_left_skip_code, tex_get_par_par(original, par_par_init_left_skip_code), 1);
1284 tex_set_par_par(copy, par_par_init_right_skip_code, tex_get_par_par(original, par_par_init_right_skip_code), 1);
1285 tex_set_par_par(copy, par_baseline_skip_code, tex_get_par_par(original, par_baseline_skip_code), 1);
1286 tex_set_par_par(copy, par_line_skip_code, tex_get_par_par(original, par_line_skip_code), 1);
1287 tex_set_par_par(copy, par_par_shape_code, tex_get_par_par(original, par_par_shape_code), 1);
1288 tex_set_par_par(copy, par_inter_line_penalties_code, tex_get_par_par(original, par_inter_line_penalties_code), 1);
1289 tex_set_par_par(copy, par_club_penalties_code, tex_get_par_par(original, par_club_penalties_code), 1);
1290 tex_set_par_par(copy, par_widow_penalties_code, tex_get_par_par(original, par_widow_penalties_code), 1);
1291 tex_set_par_par(copy, par_display_widow_penalties_code, tex_get_par_par(original, par_display_widow_penalties_code), 1);
1292 tex_set_par_par(copy, par_orphan_penalties_code, tex_get_par_par(original, par_orphan_penalties_code), 1);
1293 tex_set_par_par(copy, par_par_passes_code, tex_get_par_par(original, par_par_passes_code), 1);
1294
1295 par_end_par_tokens(copy) = par_end_par_tokens(original);
1296 tex_add_token_reference(par_end_par_tokens(original));
1297 break;
1298 case specification_node:
1299 tex_copy_specification_list(copy, original);
1300 break;
1301 default:
1302 break;
1303 }
1304 }
1305 return copy;
1306 }
1307}
1308
1309inline static void tex_aux_free_sub_node_list(halfword source)
1310{
1311 if (source) {
1312 tex_flush_node_list(source);
1313 }
1314}
1315
1316inline static void tex_aux_free_sub_node(halfword source)
1317{
1318 if (source) {
1319 tex_flush_node(source);
1320 }
1321}
1322
1323
1324
1325void tex_flush_node(halfword p)
1326{
1327 if (! p) {
1328
1329 return;
1330 } else if (p <= lmt_node_memory_state.reserved || p >= lmt_node_memory_state.nodes_data.allocated) {
1331 tex_formatted_error("nodes", "attempt to free an impossible node %d of type %d", (int) p, node_type(p));
1332 } else if (lmt_node_memory_state.nodesizes[p] == 0) {
1333 for (int i = (lmt_node_memory_state.reserved + 1); i < lmt_node_memory_state.nodes_data.allocated; i++) {
1334 if (lmt_node_memory_state.nodesizes[i] > 0) {
1335 tex_aux_check_node(i);
1336 }
1337 }
1338 tex_formatted_error("nodes", "attempt to double-free %s node %d, ignored", get_node_name(node_type(p)), (int) p);
1339 } else {
1340 int t = node_type(p);
1341 if (tex_nodetype_is_complex(t)) {
1342 switch (t) {
1343 case glue_node:
1344 tex_aux_free_sub_node_list(glue_leader_ptr(p));
1345 break;
1346 case hlist_node:
1347 tex_aux_free_sub_node_list(box_pre_adjusted(p));
1348 tex_aux_free_sub_node_list(box_post_adjusted(p));
1349
1350 case vlist_node:
1351 tex_aux_free_sub_node_list(box_pre_migrated(p));
1352 tex_aux_free_sub_node_list(box_post_migrated(p));
1353
1354 case unset_node:
1355 tex_aux_free_sub_node_list(box_list(p));
1356 break;
1357 case disc_node:
1358
1359 tex_aux_free_sub_node_list(disc_pre_break_head(p));
1360 tex_aux_free_sub_node_list(disc_post_break_head(p));
1361 tex_aux_free_sub_node_list(disc_no_break_head(p));
1362 break;
1363 case par_node:
1364 tex_aux_free_sub_node_list(par_box_left(p));
1365 tex_aux_free_sub_node_list(par_box_right(p));
1366 tex_aux_free_sub_node_list(par_box_middle(p));
1367
1368 tex_flush_node(par_left_skip(p));
1369 tex_flush_node(par_right_skip(p));
1370 tex_flush_node(par_par_fill_left_skip(p));
1371 tex_flush_node(par_par_fill_right_skip(p));
1372 tex_flush_node(par_par_init_left_skip(p));
1373 tex_flush_node(par_par_init_right_skip(p));
1374 tex_flush_node(par_emergency_left_skip(p));
1375 tex_flush_node(par_emergency_right_skip(p));
1376 tex_flush_node(par_baseline_skip(p));
1377 tex_flush_node(par_line_skip(p));
1378 tex_flush_node(par_par_shape(p));
1379 tex_flush_node(par_club_penalties(p));
1380 tex_flush_node(par_inter_line_penalties(p));
1381 tex_flush_node(par_widow_penalties(p));
1382 tex_flush_node(par_display_widow_penalties(p));
1383 tex_flush_node(par_orphan_penalties(p));
1384 tex_flush_node(par_par_passes(p));
1385
1386 tex_flush_token_list(par_end_par_tokens(p));
1387 break;
1388 case insert_node:
1389 tex_flush_node_list(insert_list(p));
1390 break;
1391 case mark_node:
1392 tex_delete_token_reference(mark_ptr(p));
1393 break;
1394 case adjust_node:
1395 tex_flush_node_list(adjust_list(p));
1396 break;
1397 case choice_node:
1398 tex_aux_free_sub_node_list(choice_display_mlist(p));
1399 tex_aux_free_sub_node_list(choice_text_mlist(p));
1400 tex_aux_free_sub_node_list(choice_script_mlist(p));
1401 tex_aux_free_sub_node_list(choice_script_script_mlist(p));
1402 break;
1403 case simple_noad:
1404 case fraction_noad:
1405 case radical_noad:
1406 case accent_noad:
1407 tex_aux_free_sub_node_list(noad_nucleus(p));
1408 tex_aux_free_sub_node_list(noad_subscr(p));
1409 tex_aux_free_sub_node_list(noad_supscr(p));
1410 tex_aux_free_sub_node_list(noad_subprescr(p));
1411 tex_aux_free_sub_node_list(noad_supprescr(p));
1412 tex_aux_free_sub_node_list(noad_prime(p));
1413
1414 switch (t) {
1415 case fraction_noad:
1416
1417
1418 tex_aux_free_sub_node(fraction_left_delimiter(p));
1419 tex_aux_free_sub_node(fraction_right_delimiter(p));
1420 tex_aux_free_sub_node(fraction_middle_delimiter(p));
1421 break;
1422 case radical_noad:
1423 tex_aux_free_sub_node(radical_left_delimiter(p));
1424 tex_aux_free_sub_node(radical_right_delimiter(p));
1425 tex_aux_free_sub_node(radical_top_delimiter(p));
1426 tex_aux_free_sub_node(radical_bottom_delimiter(p));
1427 tex_aux_free_sub_node_list(radical_degree(p));
1428 break;
1429 case accent_noad:
1430 tex_aux_free_sub_node_list(accent_top_character(p));
1431 tex_aux_free_sub_node_list(accent_bottom_character(p));
1432 tex_aux_free_sub_node_list(accent_middle_character(p));
1433 break;
1434 }
1435 break;
1436 case fence_noad:
1437 tex_aux_free_sub_node_list(fence_delimiter_list(p));
1438 tex_aux_free_sub_node_list(fence_delimiter_top(p));
1439 tex_aux_free_sub_node_list(fence_delimiter_bottom(p));
1440 break;
1441 case sub_box_node:
1442 case sub_mlist_node:
1443 tex_aux_free_sub_node_list(kernel_math_list(p));
1444 break;
1445 case specification_node:
1446 tex_dispose_specification_list(p);
1447 break;
1448 default:
1449 break;
1450 }
1451 if (tex_nodetype_has_attributes(t)) {
1452 delete_attribute_reference(node_attr(p));
1453 node_attr(p) = null;
1454 lmt_properties_reset(lmt_lua_state.lua_instance, p);
1455 }
1456 }
1457 tex_free_node(p, get_node_size(t));
1458 }
1459}
1460
1461
1462
1463void tex_flush_node_list(halfword l)
1464{
1465 if (! l) {
1466
1467 return;
1468 } else if (l <= lmt_node_memory_state.reserved || l >= lmt_node_memory_state.nodes_data.allocated) {
1469 tex_formatted_error("nodes", "attempt to free an impossible node list %d of type %d", (int) l, node_type(l));
1470 } else if (lmt_node_memory_state.nodesizes[l] == 0) {
1471 for (int i = (lmt_node_memory_state.reserved + 1); i < lmt_node_memory_state.nodes_data.allocated; i++) {
1472 if (lmt_node_memory_state.nodesizes[i] > 0) {
1473 tex_aux_check_node(i);
1474 }
1475 }
1476 tex_formatted_error("nodes", "attempt to double-free %s node %d, ignored", get_node_name(node_type(l)), (int) l);
1477 } else {
1478
1479 lua_State *L = lmt_lua_state.lua_instance;
1480 lmt_properties_push(L);
1481 while (l) {
1482 halfword nxt = node_next(l);
1483 tex_flush_node(l);
1484 l = nxt;
1485 }
1486
1487 lmt_properties_pop(L);
1488 }
1489}
1490
1491static void tex_aux_check_node(halfword p)
1492{
1493 halfword type = node_type(p);
1494 switch (type) {
1495 case glue_node:
1496 tex_aux_node_range_test(p, glue_leader_ptr(p));
1497 break;
1498 case hlist_node:
1499 tex_aux_node_range_test(p, box_pre_adjusted(p));
1500 tex_aux_node_range_test(p, box_post_adjusted(p));
1501
1502 case vlist_node:
1503 tex_aux_node_range_test(p, box_pre_migrated(p));
1504 tex_aux_node_range_test(p, box_post_migrated(p));
1505
1506 case unset_node:
1507 case align_record_node:
1508 tex_aux_node_range_test(p, box_list(p));
1509 break;
1510 case insert_node:
1511 tex_aux_node_range_test(p, insert_list(p));
1512 break;
1513 case disc_node:
1514 tex_aux_node_range_test(p, disc_pre_break_head(p));
1515 tex_aux_node_range_test(p, disc_post_break_head(p));
1516 tex_aux_node_range_test(p, disc_no_break_head(p));
1517 break;
1518 case adjust_node:
1519 tex_aux_node_range_test(p, adjust_list(p));
1520 break;
1521 case choice_node:
1522 tex_aux_node_range_test(p, choice_display_mlist(p));
1523 tex_aux_node_range_test(p, choice_text_mlist(p));
1524 tex_aux_node_range_test(p, choice_script_mlist(p));
1525 tex_aux_node_range_test(p, choice_script_script_mlist(p));
1526 break;
1527 case simple_noad:
1528 case radical_noad:
1529 case fraction_noad:
1530 case accent_noad:
1531 tex_aux_node_range_test(p, noad_nucleus(p));
1532 tex_aux_node_range_test(p, noad_subscr(p));
1533 tex_aux_node_range_test(p, noad_supscr(p));
1534 tex_aux_node_range_test(p, noad_subprescr(p));
1535 tex_aux_node_range_test(p, noad_supprescr(p));
1536 tex_aux_node_range_test(p, noad_prime(p));
1537
1538 switch (type) {
1539 case radical_noad:
1540 tex_aux_node_range_test(p, radical_degree(p));
1541 tex_aux_node_range_test(p, radical_left_delimiter(p));
1542 tex_aux_node_range_test(p, radical_right_delimiter(p));
1543 tex_aux_node_range_test(p, radical_top_delimiter(p));
1544 tex_aux_node_range_test(p, radical_bottom_delimiter(p));
1545 break;
1546 case fraction_noad:
1547
1548
1549 tex_aux_node_range_test(p, fraction_left_delimiter(p));
1550 tex_aux_node_range_test(p, fraction_right_delimiter(p));
1551 tex_aux_node_range_test(p, fraction_middle_delimiter(p));
1552 break;
1553 case accent_noad:
1554 tex_aux_node_range_test(p, accent_top_character(p));
1555 tex_aux_node_range_test(p, accent_bottom_character(p));
1556 tex_aux_node_range_test(p, accent_middle_character(p));
1557 break;
1558 }
1559 break;
1560 case fence_noad:
1561 tex_aux_node_range_test(p, fence_delimiter_list(p));
1562 tex_aux_node_range_test(p, fence_delimiter_top(p));
1563 tex_aux_node_range_test(p, fence_delimiter_bottom(p));
1564 break;
1565 case par_node:
1566 tex_aux_node_range_test(p, par_box_left(p));
1567 tex_aux_node_range_test(p, par_box_right(p));
1568 tex_aux_node_range_test(p, par_box_middle(p));
1569 tex_aux_node_range_test(p, par_left_skip(p));
1570 tex_aux_node_range_test(p, par_right_skip(p));
1571 tex_aux_node_range_test(p, par_baseline_skip(p));
1572 tex_aux_node_range_test(p, par_line_skip(p));
1573 tex_aux_node_range_test(p, par_par_shape(p));
1574 tex_aux_node_range_test(p, par_club_penalties(p));
1575 tex_aux_node_range_test(p, par_inter_line_penalties(p));
1576 tex_aux_node_range_test(p, par_widow_penalties(p));
1577 tex_aux_node_range_test(p, par_display_widow_penalties(p));
1578 tex_aux_node_range_test(p, par_orphan_penalties(p));
1579 tex_aux_node_range_test(p, par_par_fill_left_skip(p));
1580 tex_aux_node_range_test(p, par_par_fill_right_skip(p));
1581 tex_aux_node_range_test(p, par_par_init_left_skip(p));
1582 tex_aux_node_range_test(p, par_par_init_right_skip(p));
1583 tex_aux_node_range_test(p, par_emergency_left_skip(p));
1584 tex_aux_node_range_test(p, par_emergency_right_skip(p));
1585 tex_aux_node_range_test(p, par_par_passes(p));
1586 break;
1587 default:
1588 break;
1589 }
1590}
1591
1592
1609
1610halfword tex_get_node(int size)
1611{
1612 if (size < max_chain_size) {
1613 halfword p = lmt_node_memory_state.free_chain[size];
1614 if (p) {
1615 lmt_node_memory_state.free_chain[size] = node_next(p);
1616 lmt_node_memory_state.nodesizes[p] = (char) size;
1617 node_next(p) = null;
1618 lmt_node_memory_state.nodes_data.ptr += size;
1619 return p;
1620 } else {
1621 return tex_aux_allocated_node(size);
1622 }
1623 } else {
1624 return tex_normal_error("nodes", "there is a problem in getting a node, case 1");
1625 }
1626}
1627
1628void tex_free_node(halfword p, int size)
1629{
1630 if (p > lmt_node_memory_state.reserved && size < max_chain_size) {
1631 lmt_node_memory_state.nodesizes[p] = 0;
1632 node_next(p) = lmt_node_memory_state.free_chain[size];
1633 lmt_node_memory_state.free_chain[size] = p;
1634 lmt_node_memory_state.nodes_data.ptr -= size;
1635 } else {
1636 tex_formatted_error("nodes", "node number %d of type %d with size %d should not be freed", (int) p, node_type(p), size);
1637 }
1638}
1639
1640
1647
1648static void tex_aux_initialize_glue(halfword n, scaled amount, scaled stretch, scaled shrink, halfword stretchorder, halfword shrinkorder)
1649{
1650
1651 node_type(n) = glue_spec_node;
1652 glue_amount(n) = amount;
1653 glue_stretch(n) = stretch;
1654 glue_shrink(n) = shrink;
1655 glue_stretch_order(n) = stretchorder;
1656 glue_shrink_order(n) = shrinkorder;
1657}
1658
1659static void tex_aux_initialize_whatever_node(halfword n, quarterword type)
1660{
1661
1662 node_type(n) = type;
1663}
1664
1665static void tex_aux_initialize_character(halfword n, halfword chr)
1666{
1667
1668 node_type(n) = glyph_node;
1669 glyph_character(n) = chr;
1670}
1671# define reserved_node_slots 32
1672
1673void tex_initialize_node_mem()
1674{
1675 memoryword *nodes = NULL;
1676 char *sizes = NULL;
1677 int size = 0;
1678 if (lmt_main_state.run_state == initializing_state) {
1679 size = lmt_node_memory_state.nodes_data.minimum;
1680 lmt_node_memory_state.reserved = last_reserved;
1681 lmt_node_memory_state.nodes_data.top = last_reserved + 1;
1682 lmt_node_memory_state.nodes_data.allocated = size;
1683 lmt_node_memory_state.nodes_data.ptr = last_reserved;
1684 } else {
1685 size = lmt_node_memory_state.nodes_data.allocated;
1686 lmt_node_memory_state.nodes_data.initial = lmt_node_memory_state.nodes_data.ptr;
1687 }
1688 if (size >0) {
1689 nodes = aux_allocate_clear_array(sizeof(memoryword), size, reserved_node_slots);
1690 sizes = aux_allocate_clear_array(sizeof(char), size, reserved_node_slots);
1691 }
1692 if (nodes && sizes) {
1693 lmt_node_memory_state.nodes = nodes;
1694 lmt_node_memory_state.nodesizes = sizes;
1695 } else {
1696 tex_overflow_error("nodes", size);
1697 }
1698}
1699
1700void tex_initialize_nodes(void)
1701{
1702 if (lmt_main_state.run_state == initializing_state) {
1703
1704
1705 tex_aux_initialize_glue(zero_glue, 0, 0, 0, 0, 0);
1706 tex_aux_initialize_glue(fi_glue, 0, 0, 0, fi_glue_order, 0);
1707 tex_aux_initialize_glue(fi_l_glue, 0, unity, 0, fil_glue_order, 0);
1708 tex_aux_initialize_glue(fi_ll_glue, 0, unity, 0, fill_glue_order, 0);
1709 tex_aux_initialize_glue(fi_ss_glue, 0, unity, unity, fil_glue_order, fil_glue_order);
1710 tex_aux_initialize_glue(fi_l_neg_glue, 0, -unity, 0, fil_glue_order, 0);
1711
1712
1713
1714 tex_aux_initialize_whatever_node(page_insert_head, temp_node);
1715 tex_aux_initialize_whatever_node(contribute_head, temp_node);
1716 tex_aux_initialize_whatever_node(page_head, temp_node);
1717 tex_aux_initialize_whatever_node(temp_head, temp_node);
1718 tex_aux_initialize_whatever_node(hold_head, temp_node);
1719 tex_aux_initialize_whatever_node(post_adjust_head, temp_node);
1720 tex_aux_initialize_whatever_node(pre_adjust_head, temp_node);
1721 tex_aux_initialize_whatever_node(post_migrate_head, temp_node);
1722 tex_aux_initialize_whatever_node(pre_migrate_head, temp_node);
1723 tex_aux_initialize_whatever_node(align_head, temp_node);
1724 tex_aux_initialize_whatever_node(active_head, unhyphenated_node);
1725 tex_aux_initialize_whatever_node(end_span, span_node);
1726
1727 tex_aux_initialize_character(begin_period, '.');
1728 tex_aux_initialize_character(end_period, '.');
1729 }
1730}
1731
1732int tex_used_node_count(void)
1733{
1734 int used = 0;
1735 for (int i = lmt_node_memory_state.nodes_data.top; i > lmt_node_memory_state.reserved; i--) {
1736 if (lmt_node_memory_state.nodesizes[i] > 0 && (node_type(i) <= max_node_type)) {
1737 ++used;
1738 }
1739 }
1740 return used;
1741}
1742int tex_free_node_count(void)
1743{
1744 int free = 0;
1745 for (int i = 1; i < max_chain_size; i++) {
1746 halfword p = lmt_node_memory_state.free_chain[i];
1747 while (p) {
1748 ++free;
1749 p = node_next(p);
1750 }
1751 }
1752 return free;
1753}
1754
1755void tex_dump_node_mem(dumpstream f)
1756{
1757 dump_int(f, lmt_node_memory_state.nodes_data.allocated);
1758 dump_int(f, lmt_node_memory_state.nodes_data.top);
1759 dump_things(f, lmt_node_memory_state.nodes[0], (size_t) lmt_node_memory_state.nodes_data.top + 1);
1760 dump_things(f, lmt_node_memory_state.nodesizes[0], lmt_node_memory_state.nodes_data.top);
1761 dump_things(f, lmt_node_memory_state.free_chain[0], max_chain_size);
1762 dump_int(f, lmt_node_memory_state.nodes_data.ptr);
1763 dump_int(f, lmt_node_memory_state.reserved);
1764}
1765
1766
1771
1772void tex_undump_node_mem(dumpstream f)
1773{
1774 undump_int(f, lmt_node_memory_state.nodes_data.allocated);
1775 undump_int(f, lmt_node_memory_state.nodes_data.top);
1776 tex_initialize_node_mem();
1777 undump_things(f, lmt_node_memory_state.nodes[0], (size_t) lmt_node_memory_state.nodes_data.top + 1);
1778 undump_things(f, lmt_node_memory_state.nodesizes[0], (size_t) lmt_node_memory_state.nodes_data.top);
1779 undump_things(f, lmt_node_memory_state.free_chain[0], max_chain_size);
1780 undump_int(f, lmt_node_memory_state.nodes_data.ptr);
1781 undump_int(f, lmt_node_memory_state.reserved);
1782}
1783
1784static halfword tex_aux_allocated_node(int s)
1785{
1786 int old = lmt_node_memory_state.nodes_data.top;
1787 int new = old + s;
1788 if (new > lmt_node_memory_state.nodes_data.allocated) {
1789 if (lmt_node_memory_state.nodes_data.allocated + lmt_node_memory_state.nodes_data.step <= lmt_node_memory_state.nodes_data.size) {
1790 memoryword *nodes = aux_reallocate_array(lmt_node_memory_state.nodes, sizeof(memoryword), lmt_node_memory_state.nodes_data.allocated + lmt_node_memory_state.nodes_data.step, reserved_node_slots);
1791 char *sizes = aux_reallocate_array(lmt_node_memory_state.nodesizes, sizeof(char), lmt_node_memory_state.nodes_data.allocated + lmt_node_memory_state.nodes_data.step, reserved_node_slots);
1792 if (nodes && sizes) {
1793 lmt_node_memory_state.nodes = nodes;
1794 lmt_node_memory_state.nodesizes = sizes;
1795 memset((void *) (nodes + lmt_node_memory_state.nodes_data.allocated), 0, (size_t) lmt_node_memory_state.nodes_data.step * sizeof(memoryword));
1796 memset((void *) (sizes + lmt_node_memory_state.nodes_data.allocated), 0, (size_t) lmt_node_memory_state.nodes_data.step * sizeof(char));
1797 lmt_node_memory_state.nodes_data.allocated += lmt_node_memory_state.nodes_data.step;
1798 lmt_run_memory_callback("node", 1);
1799 } else {
1800 lmt_run_memory_callback("node", 0);
1801 tex_overflow_error("node memory size", lmt_node_memory_state.nodes_data.size);
1802 }
1803 }
1804 if (new > lmt_node_memory_state.nodes_data.allocated) {
1805 tex_overflow_error("node memory size", lmt_node_memory_state.nodes_data.size);
1806 }
1807 }
1808
1809
1810 lmt_node_memory_state.nodesizes[old] = (char) s;
1811 lmt_node_memory_state.nodes_data.top = new;
1812 return old;
1813}
1814
1815int tex_n_of_used_nodes(int counts[])
1816{
1817 int n = 0;
1818 for (int i = 0; i < max_node_type; i++) {
1819 counts[i] = 0;
1820 }
1821 for (int i = lmt_node_memory_state.nodes_data.top; i > lmt_node_memory_state.reserved; i--) {
1822 if (lmt_node_memory_state.nodesizes[i] > 0 && (node_type(i) <= max_node_type)) {
1823 counts[node_type(i)] += 1;
1824
1825 }
1826 }
1827 for (int i = 0; i < max_node_type; i++) {
1828 n += counts[i];
1829 }
1830 return n;
1831}
1832
1833
1834
1835halfword tex_list_node_mem_usage(void)
1836{
1837 char *saved_varmem_sizes = aux_allocate_array(sizeof(char), lmt_node_memory_state.nodes_data.allocated, 1);
1838 if (saved_varmem_sizes) {
1839 halfword q = null;
1840 halfword p = null;
1841 memcpy(saved_varmem_sizes, lmt_node_memory_state.nodesizes, (size_t) lmt_node_memory_state.nodes_data.allocated);
1842 for (halfword i = lmt_node_memory_state.reserved + 1; i < (lmt_node_memory_state.nodes_data.allocated - 1); i++) {
1843 if (saved_varmem_sizes[i] > 0) {
1844 halfword j = tex_copy_node(i);
1845 if (p) {
1846 node_next(p) = j;
1847 } else {
1848 q = j;
1849 }
1850 p = j;
1851 }
1852 }
1853 aux_deallocate_array(saved_varmem_sizes);
1854 return q;
1855 } else {
1856 return null;
1857 }
1858}
1859
1860
1864
1865extern void tex_change_attribute_register(halfword a, halfword id, halfword value)
1866{
1867 if (eq_value(id) != value) {
1868 if (is_global(a)) {
1869
1870
1871
1872
1873
1874
1875 int ptr = lmt_save_state.save_stack_data.ptr - 1;
1876 while (ptr >= 0) {
1877 if (save_type(ptr) == level_boundary_save_type) {
1878 delete_attribute_reference(save_value_2(ptr));
1879 save_value_2(ptr) = attribute_cache_disabled;
1880 if (ptr) {
1881 ptr = save_value(ptr);
1882 } else {
1883 break;
1884 }
1885 } else {
1886
1887 break;
1888 }
1889 }
1890 } else {
1891 delete_attribute_reference(current_attribute_state);
1892 }
1893 set_current_attribute_state(attribute_cache_disabled);
1894 }
1895}
1896
1897inline static halfword tex_aux_new_attribute_list_node(halfword count)
1898{
1899 halfword r = tex_get_node(attribute_node_size);
1900 node_type(r) = attribute_node;
1901 node_subtype(r) = attribute_list_subtype;
1902 attribute_unset(r) = 0;
1903 attribute_count(r) = count;
1904 return r;
1905}
1906
1907inline static halfword tex_aux_new_attribute_node(halfword index, int value)
1908{
1909 halfword r = tex_get_node(attribute_node_size);
1910 node_type(r) = attribute_node;
1911 node_subtype(r) = attribute_value_subtype;
1912 attribute_index(r) = index;
1913 attribute_value(r) = value;
1914 return r;
1915}
1916
1917inline static halfword tex_aux_copy_attribute_node(halfword n)
1918{
1919 halfword a = tex_get_node(attribute_node_size);
1920 memcpy((void *) (lmt_node_memory_state.nodes + a), (void *) (lmt_node_memory_state.nodes + n), (sizeof(memoryword) * attribute_node_size));
1921 return a;
1922}
1923
1924halfword tex_copy_attribute_list(halfword a_old)
1925{
1926 if (a_old && a_old != attribute_cache_disabled) {
1927 halfword a_new = tex_aux_new_attribute_list_node(0);
1928 halfword p_old = a_old;
1929 halfword p_new = a_new;
1930 p_old = node_next(p_old);
1931 while (p_old) {
1932 halfword a = tex_copy_node(p_old);
1933 node_next(p_new) = a;
1934 p_new = a;
1935 p_old = node_next(p_old);
1936 }
1937 node_next(p_new) = null;
1938 return a_new;
1939 } else {
1940 return a_old;
1941 }
1942}
1943
1944halfword tex_copy_attribute_list_set(halfword a_old, int index, int value)
1945{
1946 halfword a_new = tex_aux_new_attribute_list_node(0);
1947 halfword p_new = a_new;
1948 int done = 0;
1949 if (a_old && a_old != attribute_cache_disabled) {
1950 halfword p_old = node_next(a_old);
1951 while (p_old) {
1952 halfword i = attribute_index(p_old);
1953 if (! done && i >= index) {
1954 if (value != unused_attribute_value) {
1955 halfword a = tex_aux_new_attribute_node(index, value);
1956 node_next(p_new) = a;
1957 p_new = a;
1958 }
1959 done = 1;
1960 if (i == index) {
1961 goto CONTINUE;
1962 }
1963 }
1964
1965 {
1966 halfword a = tex_aux_copy_attribute_node(p_old);
1967 node_next(p_new) = a;
1968 p_new = a;
1969 }
1970 CONTINUE:
1971 p_old = node_next(p_old);
1972 }
1973 node_next(p_new) = null;
1974 }
1975 if (! done && value != unused_attribute_value) {
1976 halfword b = tex_aux_new_attribute_node(index, value);
1977 node_next(p_new) = b;
1978 }
1979 return a_new;
1980}
1981
1982static void tex_aux_update_attribute_cache(void)
1983{
1984 halfword p = tex_aux_new_attribute_list_node(0);
1985 set_current_attribute_state(p);
1986 for (int i = 0; i <= lmt_node_memory_state.max_used_attribute; i++) {
1987 int v = attribute_register(i);
1988 if (v > unused_attribute_value) {
1989 halfword r = tex_aux_new_attribute_node(i, v);
1990 node_next(p) = r;
1991 p = r;
1992 }
1993 }
1994 if (! node_next(current_attribute_state)) {
1995 tex_free_node(current_attribute_state, attribute_node_size);
1996 set_current_attribute_state(null);
1997 } else {
1998 add_attribute_reference(current_attribute_state);
1999 }
2000}
2001
2002void tex_build_attribute_list(halfword target)
2003{
2004 if (lmt_node_memory_state.max_used_attribute >= 0) {
2005 if (! current_attribute_state || current_attribute_state == attribute_cache_disabled) {
2006 tex_aux_update_attribute_cache();
2007 if (! current_attribute_state) {
2008 return;
2009 }
2010 }
2011 add_attribute_reference(current_attribute_state);
2012
2013 node_attr(target) = current_attribute_state;
2014 }
2015}
2016
2017halfword tex_current_attribute_list(void)
2018{
2019 if (lmt_node_memory_state.max_used_attribute >= 0) {
2020 if (! current_attribute_state || current_attribute_state == attribute_cache_disabled) {
2021 tex_aux_update_attribute_cache();
2022 }
2023 return current_attribute_state;
2024 } else {
2025 return null;
2026 }
2027}
2028
2029
2039
2040void tex_dereference_attribute_list(halfword a)
2041{
2042 if (a && a != attribute_cache_disabled) {
2043 if (node_type(a) == attribute_node && node_subtype(a) == attribute_list_subtype){
2044 if (attribute_count(a) > 0) {
2045 --attribute_count(a);
2046 if (attribute_count(a) == 0) {
2047 if (a == current_attribute_state) {
2048 set_current_attribute_state(attribute_cache_disabled);
2049 }
2050 {
2051 int u = 0;
2052
2053if (0) {
2054 while (a) {
2055 halfword n = node_next(a);
2056 lmt_node_memory_state.nodesizes[a] = 0;
2057 node_next(a) = lmt_node_memory_state.free_chain[attribute_node_size];
2058 lmt_node_memory_state.free_chain[attribute_node_size] = a;
2059 ++u;
2060 a = n;
2061 }
2062} else {
2063
2064 halfword h = a;
2065 halfword t = a;
2066 while (a) {
2067 lmt_node_memory_state.nodesizes[a] = 0;
2068 ++u;
2069 t = a;
2070 a = node_next(a);
2071 }
2072 node_next(t) = lmt_node_memory_state.free_chain[attribute_node_size];
2073 lmt_node_memory_state.free_chain[attribute_node_size] = h;
2074}
2075
2076 lmt_node_memory_state.nodes_data.ptr -= u * attribute_node_size;
2077 }
2078 }
2079 } else {
2080 tex_formatted_error("nodes", "zero referenced attribute list %i", a);
2081 }
2082 } else {
2083 tex_formatted_error("nodes", "trying to delete an attribute reference of a non attribute list node %i (%i)", a, node_type(a));
2084 }
2085 }
2086}
2087
2088
2091
2092halfword tex_patch_attribute_list(halfword list, int index, int value)
2093{
2094 if (list == attribute_cache_disabled) {
2095 return list;
2096 } else if (list) {
2097 halfword current = node_next(list);
2098 halfword previous = list;
2099 while (current) {
2100 int i = attribute_index(current);
2101 if (i == index) {
2102
2103 attribute_value(current) = value;
2104 return list;
2105 } else if (i > index) {
2106
2107 halfword r = tex_aux_new_attribute_node(index, value);
2108 node_next(previous) = r;
2109 node_next(r) = current;
2110 return list;
2111 } else {
2112 previous = current;
2113 current = node_next(current);
2114 }
2115 }
2116 {
2117
2118 halfword r = tex_aux_new_attribute_node(index, value);
2119 node_next(r) = node_next(previous);
2120 node_next(previous) = r;
2121 }
2122 } else {
2123
2124 halfword r = tex_aux_new_attribute_node(index, value);
2125 list = tex_aux_new_attribute_list_node(0);
2126 node_next(list) = r;
2127 }
2128 return list;
2129}
2130
2131
2132
2133void tex_set_attribute(halfword target, int index, int value)
2134{
2135
2136 if (tex_nodetype_has_attributes(node_type(target))) {
2137 if (value == unused_attribute_value) {
2138 tex_unset_attribute(target, index, value);
2139 } else {
2140
2141 halfword a = node_attr(target);
2142
2143 if (a) {
2144 halfword p = node_next(a);
2145 while (p) {
2146 int i = attribute_index(p);
2147 if (i == index) {
2148 if (attribute_value(p) == value) {
2149 return;
2150 } else {
2151 break;
2152 }
2153 } else if (i > index) {
2154 break;
2155 } else {
2156 p = node_next(p);
2157 }
2158 }
2159
2160
2161
2162
2163
2164
2165 }
2166 a = tex_copy_attribute_list_set(a, index, value);
2167 tex_attach_attribute_list_attribute(target, a);
2168 }
2169 }
2170}
2171
2172int tex_unset_attribute(halfword target, int index, int value)
2173{
2174 if (tex_nodetype_has_attributes(node_type(target))) {
2175 halfword p = node_attr(target);
2176 if (p) {
2177 halfword c = node_next(p);
2178 while (c) {
2179 halfword i = attribute_index(c);
2180 if (i == index) {
2181 halfword v = attribute_value(c);
2182 if (v != value) {
2183 halfword l = tex_copy_attribute_list_set(p, index, value);
2184 tex_attach_attribute_list_attribute(target, l);
2185 }
2186 return v;
2187 } else if (i > index) {
2188 return unused_attribute_value;
2189 }
2190 c = node_next(c);
2191 }
2192 }
2193 }
2194 return unused_attribute_value;
2195}
2196
2197void tex_unset_attributes(halfword first, halfword last, int index)
2198{
2199 halfword a = null;
2200 halfword q = null;
2201 halfword n = first;
2202 while (n) {
2203 if (tex_nodetype_has_attributes(node_type(n))) {
2204 halfword p = node_attr(n);
2205 if (p) {
2206 if (p == q) {
2207 tex_attach_attribute_list_attribute(n, a);
2208 } else {
2209 halfword c = node_next(p);
2210 while (c) {
2211 halfword i = attribute_index(c);
2212 if (i == index) {
2213 q = p;
2214 a = tex_copy_attribute_list_set(p, index, unused_attribute_value);
2215 tex_attach_attribute_list_attribute(n, a);
2216 break;
2217 } else if (i > index) {
2218 break;
2219 }
2220 c = node_next(c);
2221 }
2222 }
2223 }
2224 }
2225 if (n == last) {
2226 break;
2227 } else {
2228 n = node_next(n);
2229 }
2230 }
2231}
2232
2233int tex_has_attribute(halfword n, int index, int value)
2234{
2235 if (tex_nodetype_has_attributes(node_type(n))) {
2236 halfword p = node_attr(n);
2237 if (p) {
2238 p = node_next(p);
2239 while (p) {
2240 if (attribute_index(p) == index) {
2241 int v = attribute_value(p);
2242 if (value == v || value == unused_attribute_value) {
2243 return v;
2244 } else {
2245 return unused_attribute_value;
2246 }
2247 } else if (attribute_index(p) > index) {
2248 return unused_attribute_value;
2249 }
2250 p = node_next(p);
2251 }
2252 }
2253 }
2254 return unused_attribute_value;
2255}
2256
2257
2263
2264void tex_print_short_node_contents(halfword p)
2265{
2266 int collapsing = 0;
2267 while (p) {
2268 switch (node_type(p)) {
2269 case rule_node:
2270 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2271 tex_print_char('|');
2272 break;
2273 case glue_node:
2274 switch (node_subtype(p)) {
2275 case space_skip_glue:
2276 case xspace_skip_glue:
2277 case zero_space_skip_glue:
2278 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2279 tex_print_char(' ');
2280 break;
2281 default:
2282 goto DEFAULT;
2283 }
2284 break;
2285 case math_node:
2286 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2287 tex_print_char('$');
2288 break;
2289 case disc_node:
2290 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2291 tex_print_str("[[");
2292 tex_print_short_node_contents(disc_pre_break_head(p));
2293 tex_print_str("][");
2294 tex_print_short_node_contents(disc_post_break_head(p));
2295 tex_print_str("][");
2296 tex_print_short_node_contents(disc_no_break_head(p));
2297 tex_print_str("]]");
2298 break;
2299 case dir_node:
2300 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2301 if (node_subtype(p) == cancel_dir_subtype) {
2302 tex_print_str(" >");
2303 } else {
2304 tex_print_str(dir_direction(p) ? "<r2l " : "<l2r ");
2305 }
2306 break;
2307 case glyph_node:
2308 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2309 if (glyph_font(p) != lmt_print_state.font_in_short_display) {
2310 tex_print_font_identifier(glyph_font(p));
2311 tex_print_char(' ');
2312 lmt_print_state.font_in_short_display = glyph_font(p);
2313 }
2314 tex_print_tex_str(glyph_character(p));
2315 break;
2316 case par_node:
2317 if (collapsing) { tex_print_char(']'); collapsing = 0; }
2318 tex_print_str(par_dir(p) ? "<r2l p>" : "<l2r p>");
2319 break;
2320 default:
2321 DEFAULT:
2322 if (! collapsing) {
2323 tex_print_char('[');
2324 collapsing = 1;
2325 }
2326 tex_print_char(lmt_interface.node_data[node_type(p)].name[0]);
2327 break;
2328 }
2329 p = node_next(p);
2330 }
2331 if (collapsing) {
2332 tex_print_char(']');
2333 }
2334}
2335
2336
2347
2348void tex_print_node_list(halfword p, const char *what, int threshold, int max)
2349{
2350 if (p) {
2351 if (what) {
2352 tex_append_char('.');
2353 tex_append_char('.');
2354 tex_print_levels();
2355 tex_print_current_string();
2356 tex_print_str_esc(what);
2357 } else {
2358
2359 }
2360 tex_append_char('.');
2361 tex_append_char('.');
2362 tex_show_node_list(p, threshold, max);
2363 tex_flush_char();
2364 tex_flush_char();
2365 if (what) {
2366 tex_flush_char();
2367 tex_flush_char();
2368 }
2369 }
2370}
2371
2372
2379
2380static void tex_aux_show_attr_list(halfword p)
2381{
2382 p = node_attr(p);
2383 if (p) {
2384 int callback_id = lmt_callback_defined(get_attribute_callback);
2385 if (tracing_nodes_par > 1) {
2386 tex_print_format("<%i#%i>", p, attribute_count(p));
2387 }
2388 tex_print_char('[');
2389 p = node_next(p);
2390 while (p) {
2391 halfword k = attribute_index(p);
2392 halfword v = attribute_value(p);
2393 if (callback_id) {
2394 strnumber u = tex_save_cur_string();
2395 char *ks = NULL;
2396 char *vs = NULL;
2397 lmt_run_callback(lmt_lua_state.lua_instance, callback_id, "dd->RR", k, v, &ks, &vs);
2398 tex_restore_cur_string(u);
2399 if (ks) {
2400 tex_print_str(ks);
2401 lmt_memory_free(ks);
2402 } else {
2403 tex_print_int(k);
2404 }
2405 tex_print_char('=');
2406 if (vs) {
2407 tex_print_str(vs);
2408 lmt_memory_free(vs);
2409 } else {
2410 tex_print_int(v);
2411 }
2412 } else {
2413 tex_print_format("%i=%i", k, v);
2414 };
2415 p = node_next(p);
2416 if (p) {
2417 tex_print_char(',');
2418 }
2419 }
2420 tex_print_char(']');
2421 }
2422}
2423
2424void tex_print_name(halfword n, const char* what)
2425{
2426 tex_print_str_esc(what);
2427 if (tracing_nodes_par > 0) {
2428 tex_print_format("<%i>", n);
2429 }
2430}
2431
2432static void tex_aux_print_subtype_and_attributes_str(halfword p, const char *n)
2433{
2434 if (show_node_details_par > 0) {
2435 tex_print_format("[%s]",n);
2436 }
2437 if (show_node_details_par > 1 && tex_nodetype_has_attributes(node_type(p))) {
2438 tex_aux_show_attr_list(p);
2439 }
2440}
2441
2442void tex_print_extended_subtype(halfword p, quarterword s)
2443{
2444 halfword st = s;
2445 switch (p ? node_type(p) : simple_noad) {
2446 case hlist_node:
2447 if (s > noad_class_list_base) {
2448 st -= noad_class_list_base;
2449 }
2450 case simple_noad:
2451 case math_char_node:
2452 {
2453 int callback_id = lmt_callback_defined(get_noad_class_callback);
2454 if (callback_id) {
2455 strnumber u = tex_save_cur_string();
2456 char *v = NULL;
2457 lmt_run_callback(lmt_lua_state.lua_instance, callback_id, "d->R", st, &v);
2458 tex_restore_cur_string(u);
2459 if (v) {
2460 if (p && node_type(p) == hlist_node) {
2461 tex_print_str("math");
2462 }
2463 tex_print_str(v);
2464 lmt_memory_free(v);
2465 break;
2466 }
2467 }
2468
2469 }
2470 break;
2471 default:
2472 tex_print_int(s);
2473 break;
2474 }
2475}
2476
2477static void tex_print_subtype_and_attributes_info(halfword p, quarterword s, node_info *data)
2478{
2479 if (show_node_details_par > 0) {
2480 tex_print_char('[');
2481 if (data && data->subtypes && s >= data->first && s <= data->last) {
2482 tex_print_str(data->subtypes[s].name);
2483 } else {
2484 tex_print_extended_subtype(p, s);
2485 }
2486 tex_print_char(']');
2487 }
2488 if (show_node_details_par > 1 && tex_nodetype_has_attributes(node_type(p))) {
2489 tex_aux_show_attr_list(p);
2490 }
2491}
2492
2493static void tex_print_node_and_details(halfword p)
2494{
2495 halfword type = node_type(p);
2496 quarterword subtype = node_subtype(p);
2497 tex_print_name(p, lmt_interface.node_data[type].name);
2498 switch (type) {
2499 case temp_node:
2500 case whatsit_node:
2501 return;
2502 }
2503 tex_print_subtype_and_attributes_info(p, subtype, &lmt_interface.node_data[type]);
2504}
2505
2506static void tex_aux_print_subtype_and_attributes_int(halfword p, halfword n)
2507{
2508 if (show_node_details_par > 0) { \
2509 tex_print_format("[%i]", n);
2510 }
2511 if (show_node_details_par > 1 && tex_nodetype_has_attributes(node_type(p))) {
2512 tex_aux_show_attr_list(p);
2513 }
2514}
2515
2516const char *tex_aux_subtype_str(halfword n)
2517{
2518 if (n) {
2519 node_info *data = &lmt_interface.node_data[node_type(n)];
2520 if (data && data->subtypes && node_subtype(n) >= data->first && node_subtype(n) <= data->last) {
2521 return data->subtypes[node_subtype(n)].name;
2522 }
2523 }
2524 return "";
2525}
2526
2527
2550
2551static void tex_print_specnode(halfword v, int unit)
2552{
2553 if (tracing_nodes_par > 2) {
2554 tex_print_format("<%i>", v);
2555 }
2556 tex_print_spec(v, unit);
2557}
2558
2559void tex_aux_show_dictionary(halfword p, halfword properties, halfword group, halfword index,halfword font, halfword character)
2560{
2561 int callback_id = lmt_callback_defined(get_math_dictionary_callback);
2562 if (callback_id) {
2563 strnumber u = tex_save_cur_string();
2564 char *s = NULL;
2565 lmt_run_callback(lmt_lua_state.lua_instance, callback_id, "Nddddd->R", p, properties, group, index, font, character, &s);
2566 tex_restore_cur_string(u);
2567 if (s) {
2568 tex_print_format(", %s", s);
2569 lmt_memory_free(s);
2570 return;
2571 }
2572 }
2573 if (properties) {
2574 tex_print_format(", properties %x", properties);
2575 }
2576 if (group) {
2577 tex_print_format(", group %x", group);
2578 }
2579 if (index) {
2580 tex_print_format(", index %x", index);
2581 }
2582}
2583
2584void tex_show_node_list(halfword p, int threshold, int max)
2585{
2586 if ((int) lmt_string_pool_state.string_temp_top > threshold) {
2587 if (p > null) {
2588
2589 tex_print_format("[tracing depth %i reached]", threshold);
2590 }
2591 return;
2592 } else {
2593
2594 int n = 0;
2595 if (max <= 0) {
2596 max = 5;
2597 }
2598 while (p) {
2599 tex_print_levels();
2600 tex_print_current_string();
2601 ++n;
2602 if (n > max) {
2603
2604 halfword t = tex_tail_of_node_list(p);
2605 if (t == p) {
2606
2607 return;
2608 } else if (p == node_prev(t)) {
2609
2610 } else {
2611 tex_print_format("[tracing breadth %i reached]", max);
2612 return;
2613 }
2614 }
2615 tex_print_node_and_details(p);
2616 switch (node_type(p)) {
2617 case glyph_node:
2618 if (show_node_details_par > 0) {
2619 scaledwhd whd = tex_char_whd_from_glyph(p);
2620 if (glyph_protected(p)) {
2621 tex_print_str(", protected");
2622 }
2623
2624 if (whd.wd) {
2625 tex_print_format(", wd %p", whd.wd);
2626 }
2627 if (whd.ht) {
2628 tex_print_format(", ht %p", whd.ht);
2629 }
2630 if (whd.dp) {
2631 tex_print_format(", dp %p", whd.dp);
2632 }
2633 if (whd.ic) {
2634 tex_print_format(", ic %p", whd.ic);
2635 }
2636
2637 if (get_glyph_language(p)) {
2638 tex_print_format(", language (n=%i,l=%i,r=%i)", get_glyph_language(p), get_glyph_lhmin(p), get_glyph_rhmin(p));
2639 }
2640 if (get_glyph_script(p)) {
2641 tex_print_format(", script %i", get_glyph_script(p));
2642 }
2643 if (get_glyph_hyphenate(p)) {
2644 tex_print_format(", hyphenationmode %x", get_glyph_hyphenate(p));
2645 }
2646 if (glyph_x_offset(p)) {
2647 tex_print_format(", xoffset %p", glyph_x_offset(p));
2648 }
2649 if (glyph_y_offset(p)) {
2650 tex_print_format(", yoffset %p", glyph_y_offset(p));
2651 }
2652 if (glyph_left(p)) {
2653 tex_print_format(", left %p", glyph_left(p));
2654 }
2655 if (glyph_right(p)) {
2656 tex_print_format(", right %p", glyph_right(p));
2657 }
2658 if (glyph_raise(p)) {
2659 tex_print_format(", raise %p", glyph_raise(p));
2660 }
2661 if (glyph_expansion(p)) {
2662 tex_print_format(", expansion %i", glyph_expansion(p));
2663 }
2664 if (glyph_scale(p) && glyph_scale(p) != scaling_factor) {
2665 tex_print_format(", scale %i", glyph_scale(p));
2666 }
2667 if (glyph_x_scale(p) && glyph_x_scale(p) != scaling_factor) {
2668 tex_print_format(", xscale %i", glyph_x_scale(p));
2669 }
2670 if (glyph_y_scale(p) && glyph_y_scale(p) != scaling_factor) {
2671 tex_print_format(", yscale %i", glyph_y_scale(p));
2672 }
2673 if (glyph_data(p)) {
2674 tex_print_format(", data %i", glyph_data(p));
2675 }
2676 if (glyph_state(p)) {
2677 tex_print_format(", state %i", glyph_state(p));
2678 }
2679 if (glyph_options(p)) {
2680 tex_print_format(", options %x", glyph_options(p));
2681 }
2682 if (glyph_discpart(p)) {
2683 tex_print_format(", discpart %i", glyph_discpart(p));
2684 }
2685 tex_aux_show_dictionary(p, glyph_properties(p), glyph_group(p), glyph_index(p), glyph_font(p), glyph_character(p));
2686 }
2687 tex_print_format(", font %F, glyph %U", glyph_font(p), glyph_character(p));
2688 break;
2689 case hlist_node:
2690 case vlist_node:
2691 case unset_node:
2692
2693 if (box_width(p)) {
2694 tex_print_format(", width %p", box_width(p));
2695 }
2696 if (box_height(p)) {
2697 tex_print_format(", height %p", box_height(p));
2698 }
2699 if (box_depth(p)) {
2700 tex_print_format(", depth %p", box_depth(p));
2701 }
2702 if (node_type(p) == unset_node) {
2703
2704 if (box_span_count(p)) {
2705 tex_print_format(", columns %i", box_span_count(p) + 1);
2706 }
2707 if (box_glue_stretch(p)) {
2708 tex_print_str(", stretch ");
2709 tex_print_glue(box_glue_stretch(p), box_glue_order(p), no_unit);
2710 }
2711 if (box_glue_shrink(p)) {
2712 tex_print_str(", shrink ");
2713 tex_print_glue(box_glue_shrink(p), box_glue_sign(p), no_unit);
2714 }
2715 } else {
2716
2728 double g = (double) (box_glue_set(p));
2729 if ((g != 0.0) && (box_glue_sign(p) != normal_glue_sign)) {
2730 tex_print_str(", glue ");
2731 if (box_glue_sign(p) == shrinking_glue_sign) {
2732 tex_print_str("- ");
2733 }
2734 if (g > 20000.0 || g < -20000.0) {
2735 if (g > 0.0) {
2736 tex_print_char('>');
2737 } else {
2738 tex_print_str("< -");
2739 }
2740 tex_print_glue(20000 * unity, box_glue_order(p), no_unit);
2741 } else {
2742 tex_print_glue((scaled) glueround(unity *g), box_glue_order(p), no_unit);
2743 }
2744 }
2745 if (box_shift_amount(p) != 0) {
2746 tex_print_format(", shifted %p", box_shift_amount(p));
2747 }
2748 if (valid_direction(box_dir(p))) {
2749 tex_print_format(", direction %2", box_dir(p));
2750 }
2751 if (box_geometry(p)) {
2752 tex_print_format(", geometry %x", box_geometry(p));
2753 if (tex_has_box_geometry(p, orientation_geometry)) {
2754 tex_print_format(", orientation %x", box_orientation(p));
2755 }
2756 if (tex_has_box_geometry(p, offset_geometry)) {
2757 tex_print_format(", offset(%p,%p)", box_x_offset(p), box_y_offset(p));
2758 }
2759 if (tex_has_box_geometry(p, anchor_geometry)) {
2760 if (box_anchor(p)) {
2761 tex_print_format(", anchor %x", box_anchor(p));
2762 }
2763 if (box_source_anchor(p)) {
2764 tex_print_format(", source %i", box_source_anchor(p));
2765 }
2766 if (box_target_anchor(p)) {
2767 tex_print_format(", target %i", box_target_anchor(p));
2768 }
2769 }
2770 }
2771 if (box_index(p)) {
2772 tex_print_format(", index %i", box_index(p));
2773 }
2774 if (box_package_state(p)) {
2775 tex_print_format(", state %i", box_package_state(p));
2776 }
2777 }
2778 tex_print_node_list(box_pre_adjusted(p), "preadjusted", threshold, max);
2779 tex_print_node_list(box_pre_migrated(p), "premigrated", threshold, max);
2780 tex_print_node_list(box_list(p), "list", threshold, max);
2781 tex_print_node_list(box_post_migrated(p), "postmigrated", threshold, max);
2782 tex_print_node_list(box_post_adjusted(p), "postadjusted", threshold, max);
2783 break;
2784 case rule_node:
2785
2786 if (rule_width(p)) {
2787 tex_print_format(", width %R", rule_width(p));
2788 }
2789 if (rule_height(p)) {
2790 tex_print_format(", height %R", rule_height(p));
2791 }
2792 if (rule_depth(p)) {
2793 tex_print_format(", depth %R", rule_depth(p));
2794 }
2795 switch (node_subtype(p)) {
2796 case virtual_rule_subtype:
2797 if (rule_virtual_width(p)) {
2798 tex_print_format(", virtual width %R", rule_virtual_width(p));
2799 }
2800 if (rule_virtual_height(p)) {
2801 tex_print_format(", virtual height %R", rule_virtual_height(p));
2802 }
2803 if (rule_virtual_depth(p)) {
2804 tex_print_format(", virtual depth %R", rule_virtual_depth(p));
2805 }
2806 break;
2807 case strut_rule_subtype:
2808 if (rule_strut_font(p)) {
2809 if (rule_strut_font(p) >= rule_font_fam_offset) {
2810 tex_print_format(", family %i", rule_strut_font(p) - rule_font_fam_offset);
2811 } else {
2812 tex_print_format(", font %F", rule_strut_font(p) < 0 ? 0 : rule_strut_font(p));
2813 }
2814 }
2815 if (rule_strut_character(p)) {
2816 tex_print_format(", character %U", rule_strut_character(p));
2817 }
2818
2819 default:
2820 if (rule_left(p)) {
2821 tex_print_format(", left / top %R", rule_left(p));
2822 }
2823 if (rule_right(p)) {
2824 tex_print_format(", right / bottom %R", rule_right(p));
2825 }
2826 break;
2827 }
2828 if (rule_x_offset(p)) {
2829 tex_print_format(", xoffset %R", rule_x_offset(p));
2830 }
2831 if (rule_y_offset(p)) {
2832 tex_print_format(", yoffset %R", rule_y_offset(p));
2833 }
2834 if (rule_data(p)) {
2835 tex_print_format(", data %R", rule_data(p));
2836 }
2837 break;
2838 case insert_node:
2839
2840 tex_print_format(
2841 ", index %i, total height %p, max depth %p, split glue (",
2842 insert_index(p),
2843 insert_total_height(p),
2844 insert_max_depth(p)
2845 );
2846 tex_print_specnode(insert_split_top(p), no_unit);
2847 tex_print_format(
2848 "), float cost %i",
2849 insert_float_cost(p)
2850 );
2851 tex_print_node_list(insert_list(p), "list", threshold, max);
2852 break;
2853 case dir_node:
2854 tex_print_format(", direction %2, level %i", dir_direction(p), dir_level(p));
2855 break;
2856 case par_node:
2857 {
2858 halfword v;
2859
2860 tex_print_format(", direction %2", par_dir(p));
2861 if (node_subtype(p) == vmode_par_par_subtype) {
2862 if (tex_par_state_is_set(p, par_par_shape_code) ) { v = par_par_shape(p) ; if (v) { tex_print_str(", parshape * "); } }
2863 if (tex_par_state_is_set(p, par_inter_line_penalties_code) ) { v = par_inter_line_penalties(p) ; if (v) { tex_print_str(", interlinepenalties * "); } }
2864 if (tex_par_state_is_set(p, par_club_penalties_code) ) { v = par_club_penalties(p) ; if (v) { tex_print_str(", clubpenalties * "); } }
2865 if (tex_par_state_is_set(p, par_widow_penalties_code) ) { v = par_widow_penalties(p) ; if (v) { tex_print_str(", widowpenalties * "); } }
2866 if (tex_par_state_is_set(p, par_display_widow_penalties_code) ) { v = par_display_widow_penalties(p) ; if (v) { tex_print_str(", displaywidowpenalties * "); } }
2867 if (tex_par_state_is_set(p, par_orphan_penalties_code) ) { v = par_orphan_penalties(p) ; if (v) { tex_print_str(", orphanpenalties * "); } }
2868 if (tex_par_state_is_set(p, par_hang_indent_code) ) { v = par_hang_indent(p) ; if (v) { tex_print_str(", hangindent "); tex_print_dimension(v, pt_unit); } }
2869 if (tex_par_state_is_set(p, par_hang_after_code) ) { v = par_hang_after(p) ; if (v) { tex_print_str(", hangafter "); tex_print_int (v); } }
2870 if (tex_par_state_is_set(p, par_hsize_code) ) { v = par_hsize(p) ; if (v) { tex_print_str(", hsize "); tex_print_dimension(v, pt_unit); } }
2871 if (tex_par_state_is_set(p, par_right_skip_code) ) { v = par_right_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", rightskip "); tex_print_specnode (v, pt_unit); } }
2872 if (tex_par_state_is_set(p, par_left_skip_code) ) { v = par_left_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", leftskip "); tex_print_specnode (v, pt_unit); } }
2873 if (tex_par_state_is_set(p, par_last_line_fit_code) ) { v = par_last_line_fit(p) ; if (v) { tex_print_str(", lastlinefit "); tex_print_int (v); } }
2874 if (tex_par_state_is_set(p, par_pre_tolerance_code) ) { v = par_pre_tolerance(p) ; if (v) { tex_print_str(", pretolerance "); tex_print_int (v); } }
2875 if (tex_par_state_is_set(p, par_tolerance_code) ) { v = par_tolerance(p) ; if (v) { tex_print_str(", tolerance "); tex_print_int (v); } }
2876 if (tex_par_state_is_set(p, par_looseness_code) ) { v = par_looseness(p) ; if (v) { tex_print_str(", looseness "); tex_print_int (v); } }
2877 if (tex_par_state_is_set(p, par_adjust_spacing_code) ) { v = par_adjust_spacing(p) ; if (v) { tex_print_str(", adjustspacing "); tex_print_int (v); } }
2878 if (tex_par_state_is_set(p, par_adj_demerits_code) ) { v = par_adj_demerits(p) ; if (v) { tex_print_str(", adjdemerits "); tex_print_int (v); } }
2879 if (tex_par_state_is_set(p, par_double_adj_demerits_code) ) { v = par_double_adj_demerits(p) ; if (v) { tex_print_str(", doubleadjdemerits "); tex_print_int (v); } }
2880 if (tex_par_state_is_set(p, par_protrude_chars_code) ) { v = par_protrude_chars(p) ; if (v) { tex_print_str(", protrudechars "); tex_print_int (v); } }
2881 if (tex_par_state_is_set(p, par_line_penalty_code) ) { v = par_line_penalty(p) ; if (v) { tex_print_str(", linepenalty "); tex_print_int (v); } }
2882 if (tex_par_state_is_set(p, par_double_hyphen_demerits_code) ) { v = par_double_hyphen_demerits(p) ; if (v) { tex_print_str(", doublehyphendemerits "); tex_print_int (v); } }
2883 if (tex_par_state_is_set(p, par_final_hyphen_demerits_code) ) { v = par_final_hyphen_demerits(p) ; if (v) { tex_print_str(", finalhyphendemerits "); tex_print_int (v); } }
2884 if (tex_par_state_is_set(p, par_inter_line_penalty_code) ) { v = par_inter_line_penalty(p) ; if (v) { tex_print_str(", interlinepenalty "); tex_print_int (v); } }
2885 if (tex_par_state_is_set(p, par_club_penalty_code) ) { v = par_club_penalty(p) ; if (v) { tex_print_str(", clubpenalty "); tex_print_int (v); } }
2886 if (tex_par_state_is_set(p, par_widow_penalty_code) ) { v = par_widow_penalty(p) ; if (v) { tex_print_str(", widowpenalty "); tex_print_int (v); } }
2887 if (tex_par_state_is_set(p, par_display_widow_penalty_code) ) { v = par_display_widow_penalty(p) ; if (v) { tex_print_str(", displaywidowpenalty "); tex_print_int (v); } }
2888 if (tex_par_state_is_set(p, par_orphan_penalty_code) ) { v = par_orphan_penalty(p) ; if (v) { tex_print_str(", orphanpenalty "); tex_print_int (v); } }
2889 if (tex_par_state_is_set(p, par_single_line_penalty_code) ) { v = par_single_line_penalty(p) ; if (v) { tex_print_str(", singlelinepenalty "); tex_print_int (v); } }
2890 if (tex_par_state_is_set(p, par_broken_penalty_code) ) { v = par_broken_penalty(p) ; if (v) { tex_print_str(", brokenpenalty "); tex_print_int (v); } }
2891 if (tex_par_state_is_set(p, par_emergency_stretch_code) ) { v = par_emergency_stretch(p) ; if (v) { tex_print_str(", emergencystretch "); tex_print_dimension(v, pt_unit); } }
2892 if (tex_par_state_is_set(p, par_par_indent_code) ) { v = par_par_indent(p) ; if (v) { tex_print_str(", parindent "); tex_print_dimension(v, pt_unit); } }
2893 if (tex_par_state_is_set(p, par_par_fill_left_skip_code) ) { v = par_par_fill_left_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", parfilleftskip "); tex_print_specnode (v, pt_unit); } }
2894 if (tex_par_state_is_set(p, par_par_fill_right_skip_code) ) { v = par_par_fill_right_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", parfillskip "); tex_print_specnode (v, pt_unit); } }
2895 if (tex_par_state_is_set(p, par_par_init_left_skip_code) ) { v = par_par_init_left_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", parinitleftskip "); tex_print_specnode (v, pt_unit); } }
2896 if (tex_par_state_is_set(p, par_par_init_right_skip_code) ) { v = par_par_init_right_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", parinitrightskip "); tex_print_specnode (v, pt_unit); } }
2897 if (tex_par_state_is_set(p, par_emergency_left_skip_code) ) { v = par_emergency_left_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", emergencyleftskip "); tex_print_specnode (v, pt_unit); } }
2898 if (tex_par_state_is_set(p, par_emergency_right_skip_code) ) { v = par_emergency_right_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", emergencyrightskip "); tex_print_specnode (v, pt_unit); } }
2899 if (tex_par_state_is_set(p, par_baseline_skip_code) ) { v = par_baseline_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", baselineskip "); tex_print_specnode (v, pt_unit); } }
2900 if (tex_par_state_is_set(p, par_line_skip_code) ) { v = par_line_skip(p) ; if (! tex_glue_is_zero(v)) { tex_print_str(", lineskip "); tex_print_specnode (v, pt_unit); } }
2901 if (tex_par_state_is_set(p, par_line_skip_limit_code) ) { v = par_line_skip_limit(p) ; if (v) { tex_print_str(", lineskiplimt "); tex_print_dimension(v, pt_unit); } }
2902 if (tex_par_state_is_set(p, par_adjust_spacing_step_code) ) { v = par_adjust_spacing_step(p) ; if (v > 0) { tex_print_str(", adjustspacingstep "); tex_print_int (v); } }
2903 if (tex_par_state_is_set(p, par_adjust_spacing_shrink_code) ) { v = par_adjust_spacing_shrink(p) ; if (v > 0) { tex_print_str(", adjustspacingshrink "); tex_print_int (v); } }
2904 if (tex_par_state_is_set(p, par_adjust_spacing_stretch_code) ) { v = par_adjust_spacing_stretch(p) ; if (v > 0) { tex_print_str(", adjustspacingstretch "); tex_print_int (v); } }
2905 if (tex_par_state_is_set(p, par_hyphenation_mode_code) ) { v = par_hyphenation_mode(p) ; if (v > 0) { tex_print_str(", hyphenationmode "); tex_print_int (v); } }
2906 if (tex_par_state_is_set(p, par_shaping_penalties_mode_code) ) { v = par_shaping_penalties_mode(p) ; if (v > 0) { tex_print_str(", shapingpenaltiesmode "); tex_print_int (v); } }
2907 if (tex_par_state_is_set(p, par_shaping_penalty_code) ) { v = par_shaping_penalty(p) ; if (v > 0) { tex_print_str(", shapingpenalty "); tex_print_int (v); } }
2908 if (tex_par_state_is_set(p, par_emergency_extra_stretch_code) ) { v = par_emergency_extra_stretch(p) ; if (v) { tex_print_str(", emergencyextrastretch "); tex_print_dimension(v, pt_unit); } }
2909 if (tex_par_state_is_set(p, par_par_passes_code) ) { v = par_par_passes(p) ; if (v) { tex_print_str(", parpasses * "); } }
2910 }
2911
2912 v = tex_get_local_left_width(p) ; if (v) { tex_print_format(", leftboxwidth %p", v); }
2913 v = tex_get_local_right_width(p) ; if (v) { tex_print_format(", rightboxwidth %p", v); }
2914 tex_print_node_list(par_box_left(p), "leftbox", threshold, max);
2915 tex_print_node_list(par_box_right(p), "rightbox", threshold, max);
2916 tex_print_node_list(par_box_middle(p), "middlebox", threshold, max);
2917 }
2918 break;
2919 case boundary_node:
2920 if (boundary_data(p)) {
2921 tex_print_format(", data %i", boundary_data(p));
2922 }
2923 break;
2924 case whatsit_node:
2925 {
2926 int callback_id = lmt_callback_defined(show_whatsit_callback);
2927
2928 if (callback_id) {
2929 strnumber u = tex_save_cur_string();
2930 char *s = NULL;
2931 lmt_run_callback(lmt_lua_state.lua_instance, callback_id, "Nd->S", p, 1, &s);
2932 tex_restore_cur_string(u);
2933 if (s) {
2934 tex_aux_print_subtype_and_attributes_str(p, s);
2935 lmt_memory_free(s);
2936 } else {
2937 tex_aux_print_subtype_and_attributes_int(p, node_subtype(p));
2938 }
2939 } else {
2940 tex_aux_print_subtype_and_attributes_int(p, node_subtype(p));
2941 }
2942
2943 if (callback_id) {
2944 int l = lmt_string_pool_state.string_temp_top / 2;
2945 strnumber u = tex_save_cur_string();
2946
2947 lmt_run_callback(lmt_lua_state.lua_instance, callback_id, "Nddddd->", p, 2, l, (tracing_levels_par & (tracing_levels_group | tracing_levels_input)), cur_level, lmt_input_state.input_stack_data.ptr);
2948 tex_restore_cur_string(u);
2949 }
2950 }
2951 break;
2952 case glue_node:
2953
2954 if (is_leader(p)) {
2955
2956 tex_print_str(", leader ");
2957 tex_print_specnode(p, no_unit);
2958 tex_print_node_list(glue_leader_ptr(p), "list", threshold, max);
2959 } else {
2960 if (node_subtype(p) != conditional_math_glue && node_subtype(p) != rulebased_math_glue) {
2961 tex_print_char(' ');
2962 tex_print_specnode(p, node_subtype(p) < conditional_math_glue ? pt_unit : mu_unit);
2963 }
2964 if (glue_data(p)) {
2965 tex_print_format(", data %i", glue_data(p));
2966 }
2967 if (node_subtype(p) == space_skip_glue && glue_font(p)) {
2968 tex_print_format(", font %i", glue_font(p));
2969 }
2970 if (glue_options(p)) {
2971 tex_print_format(", options %x", glue_options(p));
2972 }
2973 }
2974 break;
2975 case kern_node:
2976
2977 if (node_subtype(p) != explicit_math_kern_subtype) {
2978 tex_print_format(", amount %p", kern_amount(p));
2979 if (kern_expansion(p)) {
2980 tex_print_format(", expansion %i", kern_expansion(p));
2981 }
2982 } else {
2983 tex_print_format(", amount %D", kern_amount(p), mu_unit);
2984 }
2985 break;
2986 case math_node:
2987
2988 if (! tex_math_glue_is_zero(p)) {
2989 tex_print_str(", glued ");
2990 tex_print_specnode(p, no_unit);
2991 } else if (math_surround(p)) {
2992 tex_print_format(", surrounded %p", math_surround(p));
2993 }
2994 if (math_penalty(p)) {
2995 tex_print_format(", penalty %i", math_penalty(p));
2996 }
2997 if (math_pre_tolerance(p)) {
2998 tex_print_format(", pretolerance %i", math_pre_tolerance(p));
2999 }
3000 if (math_tolerance(p)) {
3001 tex_print_format(", tolerance %i", math_tolerance(p));
3002 }
3003 if (math_options(p)) {
3004 tex_print_format(", options %x", math_options(p));
3005 }
3006 break;
3007 case penalty_node:
3008
3009 tex_print_format(", amount %i", penalty_amount(p));
3010 break;
3011 case disc_node:
3012 if (disc_class(p) != unset_disc_class) {
3013 tex_print_format(", class %i", disc_class(p));
3014 }
3015 if (disc_options(p)) {
3016 tex_print_format(", options %x", disc_options(p));
3017 }
3018 tex_print_format(", penalty %i", disc_penalty(p));
3019 tex_print_node_list(disc_pre_break_head(p), "prebreaklist", threshold, max);
3020 tex_print_node_list(disc_post_break_head(p), "postbreaklist", threshold, max);
3021 tex_print_node_list(disc_no_break_head(p), "nobreaklist", threshold, max);
3022 break;
3023 case mark_node:
3024
3025 tex_print_format(", index %i", mark_index(p));
3026 if (node_subtype(p) == reset_mark_value_code) {
3027 tex_print_str(", reset");
3028 } else {
3029 tex_print_token_list(NULL, token_link(mark_ptr(p)));
3030 }
3031 break;
3032 case adjust_node:
3033
3034 if (adjust_options(p)) {
3035 tex_print_format(", options %x", adjust_options(p));
3036 }
3037 if (adjust_index(p)) {
3038 tex_print_format(", index %i", adjust_index(p));
3039 }
3040 if (has_adjust_option(p, adjust_option_depth_before) && adjust_depth_before(p)) {
3041 tex_print_format(", depthbefore %p", adjust_depth_before(p));
3042 }
3043 if (has_adjust_option(p, adjust_option_depth_after) &&adjust_depth_before(p)) {
3044 tex_print_format(", depthafter %p", adjust_depth_after(p));
3045 }
3046 tex_print_node_list(adjust_list(p), "list", threshold, max);
3047 break;
3048 case glue_spec_node:
3049 case math_spec_node:
3050 case font_spec_node:
3051
3052 break;
3053 case align_record_node:
3054 tex_print_token_list(NULL, align_record_pre_part(p));
3055 tex_print_levels();
3056 tex_print_str("..<content>");
3057 tex_print_token_list(NULL, align_record_post_part(p));
3058 break;
3059 case temp_node:
3060 break;
3061 default:
3062 if (! tex_show_math_node(p, threshold, max)) {
3063 tex_print_format("<unknown node type %i>", node_type(p));
3064 }
3065 break;
3066 }
3067 p = node_next(p);
3068 }
3069 }
3070}
3071
3072
3078
3079static halfword tex_aux_get_actual_box_width(halfword r, halfword p, scaled initial_width)
3080{
3081
3082 scaled w = -max_dimension;
3083
3084 scaled v = initial_width;
3085 while (p) {
3086
3087 scaled d;
3088 switch (node_type(p)) {
3089 case glyph_node:
3090 d = tex_glyph_width(p);
3091 goto FOUND;
3092 case hlist_node:
3093 case vlist_node:
3094 d = box_width(p);
3095 goto FOUND;
3096 case rule_node:
3097 d = rule_width(p);
3098 goto FOUND;
3099 case kern_node:
3100 d = kern_amount(p);
3101 break;
3102 case disc_node:
3103
3104 if (disc_no_break(p)) {
3105 d = tex_aux_get_actual_box_width(r, disc_no_break_head(p),0);
3106 if (d <= -max_dimension || d >= max_dimension) {
3107 d = 0;
3108 }
3109 } else {
3110 d = 0;
3111 }
3112 goto FOUND;
3113 case math_node:
3114 if (tex_math_glue_is_zero(p)) {
3115 d = math_surround(p);
3116 } else {
3117 d = math_amount(p);
3118 switch (box_glue_sign(r)) {
3119 case stretching_glue_sign:
3120 if ((box_glue_order(r) == math_stretch_order(p)) && math_stretch(p)) {
3121 v = max_dimension;
3122 }
3123 break;
3124 case shrinking_glue_sign:
3125 if ((box_glue_order(r) == math_shrink_order(p)) && math_shrink(p)) {
3126 v = max_dimension;
3127 }
3128 break;
3129 }
3130 break;
3131 }
3132 break;
3133 case glue_node:
3134
3141 d = glue_amount(p);
3142 if (box_glue_sign(r) == stretching_glue_sign) {
3143 if ((box_glue_order(r) == glue_stretch_order(p)) && glue_stretch(p)) {
3144 v = max_dimension;
3145 }
3146 } else if (box_glue_sign(r) == shrinking_glue_sign) {
3147 if ((box_glue_order(r) == glue_shrink_order(p)) && glue_shrink(p)) {
3148 v = max_dimension;
3149 }
3150 }
3151 if (is_leader(p)) {
3152 goto FOUND;
3153 }
3154 break;
3155 default:
3156 d = 0;
3157 break;
3158 }
3159 if (v < max_dimension) {
3160 v += d;
3161 }
3162 goto NOT_FOUND;
3163 FOUND:
3164 if (v < max_dimension) {
3165 v += d;
3166 w = v;
3167 } else {
3168 w = max_dimension;
3169 break;
3170 }
3171 NOT_FOUND:
3172 p = node_next(p);
3173 }
3174 return w;
3175}
3176
3177halfword tex_actual_box_width(halfword r, scaled base_width)
3178{
3179
3188 return tex_aux_get_actual_box_width(r, box_list(r), box_shift_amount(r) + base_width);
3189}
3190
3191int tex_list_has_glyph(halfword list)
3192{
3193 while (list) {
3194 switch (node_type(list)) {
3195 case glyph_node:
3196 case disc_node:
3197 return 1;
3198 default:
3199 list = node_next(list);
3200 break;
3201 }
3202 }
3203 return 0;
3204}
3205
3206
3245
3246
3247
3248halfword tex_new_null_box_node(quarterword t, quarterword s)
3249{
3250
3251 halfword p = tex_new_node(t, s);
3252 box_dir(p) = (singleword) text_direction_par;
3253 return p;
3254}
3255
3256
3270
3271halfword tex_new_rule_node(quarterword s)
3272{
3273 return tex_new_node(rule_node, s);
3274}
3275
3276
3316
3317halfword tex_new_glyph_node(quarterword s, halfword f, halfword c, halfword parent)
3318{
3319 halfword p = parent && node_type(parent) == glyph_node ? tex_copy_node(parent) : tex_aux_new_glyph_node_with_attributes(parent);
3320 node_subtype(p) = s;
3321 glyph_font(p) = f;
3322 glyph_character(p) = c;
3323 tex_char_process(f, c);
3324 return p;
3325}
3326
3327
3348
3349
3360
3361halfword tex_new_char_node(quarterword subtype, halfword fnt, halfword chr, int all)
3362{
3363 halfword p = tex_aux_new_glyph_node_with_attributes(null);
3364 node_subtype(p) = subtype;
3365 glyph_font(p) = fnt;
3366 glyph_character(p) = chr;
3367 if (all) {
3368 glyph_data(p) = glyph_data_par;
3369
3370 set_glyph_script(p, glyph_script_par);
3371 set_glyph_language(p, cur_lang_par);
3372 set_glyph_lhmin(p, left_hyphen_min_par);
3373 set_glyph_rhmin(p, right_hyphen_min_par);
3374 set_glyph_hyphenate(p, hyphenation_mode_par);
3375 set_glyph_options(p, glyph_options_par);
3376 set_glyph_scale(p, glyph_scale_par);
3377 set_glyph_x_scale(p, glyph_x_scale_par);
3378 set_glyph_y_scale(p, glyph_y_scale_par);
3379 set_glyph_x_offset(p, glyph_x_offset_par);
3380 set_glyph_y_offset(p, glyph_y_offset_par);
3381 set_glyph_slant(p, glyph_slant_par);
3382 set_glyph_weight(p, glyph_weight_par);
3383 }
3384 if (! tex_char_exists(fnt, chr)) {
3385 int callback_id = lmt_callback_defined(missing_character_callback);
3386 if (callback_id > 0) {
3387
3388 lmt_run_callback(lmt_lua_state.lua_instance, callback_id, "Ndd->", p, fnt, chr);
3389 }
3390 }
3391 return p;
3392}
3393
3394halfword tex_new_text_glyph(halfword fnt, halfword chr)
3395{
3396 halfword p = tex_get_node(glyph_node_size);
3397 memset((void *) (lmt_node_memory_state.nodes + p + 1), 0, (sizeof(memoryword) * (glyph_node_size - 1)));
3398 node_type(p) = glyph_node;
3399 node_subtype(p) = glyph_unset_subtype;
3400 glyph_font(p) = fnt;
3401 glyph_character(p) = chr;
3402 glyph_data(p) = glyph_data_par;
3403
3404 set_glyph_script(p, glyph_script_par);
3405 set_glyph_language(p, cur_lang_par);
3406 set_glyph_lhmin(p, left_hyphen_min_par);
3407 set_glyph_rhmin(p, right_hyphen_min_par);
3408 set_glyph_hyphenate(p, hyphenation_mode_par);
3409 set_glyph_options(p, glyph_options_par);
3410 set_glyph_scale(p, glyph_scale_par);
3411 set_glyph_x_scale(p, glyph_x_scale_par);
3412 set_glyph_y_scale(p, glyph_y_scale_par);
3413 set_glyph_x_offset(p, glyph_x_offset_par);
3414 set_glyph_y_offset(p, glyph_y_offset_par);
3415 set_glyph_slant(p, glyph_slant_par);
3416 set_glyph_weight(p, glyph_weight_par);
3417 return p;
3418}
3419
3420
3439
3440
3441
3442scaled tex_glyph_width(halfword p)
3443{
3444 scaled w = tex_char_width_from_glyph(p);
3445 scaled x = glyph_x_offset(p);
3446 if (x && tex_has_glyph_option(p, glyph_option_apply_x_offset)) {
3447 w += x;
3448 }
3449 w -= (glyph_left(p) + glyph_right(p));
3450 return w;
3451}
3452
3453scaled tex_glyph_width_ex(halfword p)
3454{
3455 scaled w = tex_char_width_from_glyph(p);
3456 scaled x = glyph_x_offset(p);
3457 if (x && tex_has_glyph_option(p, glyph_option_apply_x_offset)) {
3458 w += x;
3459 }
3460 w -= (glyph_left(p) + glyph_right(p));
3461 if (glyph_expansion(p)) {
3462 w = w + tex_ext_xn_over_d(w, scaling_factor_squared + glyph_expansion(p), scaling_factor_squared);
3463 }
3464 return w;
3465}
3466
3467scaled tex_glyph_height(halfword p)
3468{
3469 scaled h = tex_char_height_from_glyph(p) + glyph_raise(p);
3470 scaled y = glyph_y_offset(p);
3471 if (y && tex_has_glyph_option(p, glyph_option_apply_y_offset)) {
3472 h += y;
3473 }
3474 return h < 0 ? 0 : h;
3475}
3476
3477scaled tex_glyph_depth(halfword p)
3478{
3479 scaled d = tex_char_depth_from_glyph(p) - glyph_raise(p);
3480 scaled y = glyph_y_offset(p);
3481 if (y && tex_has_glyph_option(p, glyph_option_apply_y_offset)) {
3482 d -= y;
3483 }
3484 return d < 0 ? 0 : d;
3485}
3486
3487scaledwhd tex_glyph_dimensions(halfword p)
3488{
3489 scaledwhd whd = tex_char_whd_from_glyph(p);
3490 scaled x = glyph_x_offset(p);
3491 scaled y = glyph_y_offset(p);
3492 whd.ht += glyph_raise(p);
3493 whd.dp -= glyph_raise(p);
3494 whd.wd += (glyph_left(p) + glyph_right(p));
3495 if (x && tex_has_glyph_option(p, glyph_option_apply_x_offset)) {
3496 whd.wd += x;
3497 }
3498 if (y && tex_has_glyph_option(p, glyph_option_apply_y_offset)) {
3499 whd.ht += y;
3500 whd.dp -= y;
3501 }
3502 if (whd.ht < 0) {
3503 whd.ht = 0;
3504 }
3505 if (whd.dp < 0) {
3506 whd.dp = 0;
3507 }
3508 return whd;
3509}
3510
3511scaledwhd tex_glyph_dimensions_ex(halfword p)
3512{
3513 scaledwhd whd = tex_char_whd_from_glyph(p);
3514 scaled x = glyph_x_offset(p);
3515 scaled y = glyph_y_offset(p);
3516 whd.ht += glyph_raise(p);
3517 whd.dp -= glyph_raise(p);
3518 whd.wd -= (glyph_left(p) + glyph_right(p));
3519 if (x && tex_has_glyph_option(p, glyph_option_apply_x_offset)) {
3520 whd.wd += x;
3521 }
3522 if (y && tex_has_glyph_option(p, glyph_option_apply_y_offset)) {
3523 whd.ht += y;
3524 whd.dp -= y;
3525 }
3526 if (whd.ht < 0) {
3527 whd.ht = 0;
3528 }
3529 if (whd.dp < 0) {
3530 whd.dp = 0;
3531 }
3532 if (whd.wd && glyph_expansion(p)) {
3533 whd.wd = tex_ext_xn_over_d(whd.wd, scaling_factor_squared + glyph_expansion(p), scaling_factor_squared);
3534 }
3535 return whd;
3536}
3537
3538scaled tex_glyph_total(halfword p)
3539{
3540 return tex_char_total_from_glyph(p);
3541}
3542
3543int tex_glyph_has_dimensions(halfword p)
3544{
3545 scaledwhd whd = tex_char_whd_from_glyph(p);
3546 scaled offset = glyph_x_offset(p);
3547 scaled amount = whd.wd;
3548 if (offset && tex_has_glyph_option(p, glyph_option_apply_x_offset)) {
3549 amount += offset;
3550 }
3551 amount -= (glyph_left(p) + glyph_right(p));
3552 if (amount) {
3553 return 1;
3554 } else {
3555
3556 return whd.ht > 0 || whd.dp > 0;
3557 }
3558}
3559
3560halfword tex_kern_dimension(halfword p)
3561{
3562 return kern_amount(p);
3563}
3564
3565halfword tex_kern_dimension_ex(halfword p)
3566{
3567 halfword k = kern_amount(p);
3568 if (k && kern_expansion(p)) {
3569 k = tex_ext_xn_over_d(k, scaling_factor_squared + kern_expansion(p), scaling_factor_squared);
3570 }
3571 return k;
3572}
3573
3574scaledwhd tex_pack_dimensions(halfword p)
3575{
3576 scaledwhd siz = { .wd = 0, .ht = 0, .dp = 0, .ns = 0 };
3577 siz.ht = box_height(p);
3578 siz.dp = box_depth(p);
3579 siz.wd = box_width(p);
3580 return siz;
3581}
3582
3583
3599
3600halfword tex_new_disc_node(quarterword s)
3601{
3602 halfword p = tex_new_node(disc_node, s);
3603 disc_penalty(p) = hyphen_penalty_par;
3604 disc_class(p) = unset_disc_class;
3605 set_disc_options(p, discretionary_options_par);
3606 return p;
3607}
3608
3609
3733
3734halfword tex_new_glue_spec_node(halfword q)
3735{
3736 if (q) {
3737 switch (node_type(q)) {
3738 case glue_spec_node:
3739 return tex_copy_node(q);
3740 case glue_node:
3741 {
3742 halfword p = tex_copy_node(zero_glue);
3743 glue_amount(p) = glue_amount(q);
3744 glue_stretch(p) = glue_stretch(q);
3745 glue_shrink(p) = glue_shrink(q);
3746 glue_stretch_order(p) = glue_stretch_order(q);
3747 glue_shrink_order(p) = glue_shrink_order(q);
3748 return p;
3749 }
3750 }
3751 }
3752 return tex_copy_node(zero_glue);
3753}
3754
3755
3762
3763halfword tex_new_param_glue_node(quarterword p, quarterword s)
3764{
3765 halfword n = tex_new_node(glue_node, s);
3766 halfword g = glue_parameter(p);
3767 if (g) {
3768 memcpy((void *) (lmt_node_memory_state.nodes + n + 2), (void *) (lmt_node_memory_state.nodes + g + 2), (glue_spec_size - 2) * (sizeof(memoryword)));
3769 }
3770 return n;
3771}
3772
3773
3779
3780halfword tex_new_glue_node(halfword q, quarterword s)
3781{
3782 halfword p = tex_new_node(glue_node, s);
3783 memcpy((void *) (lmt_node_memory_state.nodes + p + 2), (void *) (lmt_node_memory_state.nodes + q + 2), (glue_spec_size - 2) * (sizeof(memoryword)));
3784 return p;
3785}
3786
3787
3797
3798
3812
3813halfword tex_new_kern_node(scaled w, quarterword s)
3814{
3815 halfword p = tex_new_node(kern_node, s);
3816 kern_amount(p) = w;
3817 return p;
3818}
3819
3820
3831
3832halfword tex_new_penalty_node(halfword m, quarterword s)
3833{
3834 halfword p = tex_new_node(penalty_node, s);
3835 penalty_amount(p) = m;
3836 return p;
3837}
3838
3839
3871
3872halfword tex_new_par_node(quarterword subtype)
3873{
3874 int callback_id, top;
3875 halfword p = tex_new_node(par_node, subtype);
3876
3877 if (subtype == parameter_par_subtype) {
3878 tex_set_local_interline_penalty(p, local_interline_penalty_par);
3879 tex_set_local_broken_penalty(p, local_broken_penalty_par);
3880 tex_set_local_tolerance(p, local_tolerance_par);
3881 tex_set_local_pre_tolerance(p, local_pre_tolerance_par);
3882 }
3883 par_dir(p) = par_direction_par;
3884
3885 tex_add_local_boxes(p);
3886 if (subtype != local_box_par_subtype) {
3887
3888 callback_id = lmt_callback_defined(insert_par_callback);
3889 if (callback_id > 0) {
3890 lua_State *L = lmt_lua_state.lua_instance;
3891 if (lmt_callback_okay(L, callback_id, &top)) {
3892 int i;
3893 lmt_node_list_to_lua(L, p);
3894 lmt_push_par_mode(L, subtype);
3895 i = lmt_callback_call(L, 2, 0 ,top);
3896 if (i) {
3897 lmt_callback_error(L, top, i);
3898 } else {
3899 lmt_callback_wrapup(L, top);
3900 }
3901 }
3902 }
3903 }
3904 return p;
3905}
3906
3907static halfword tex_aux_internal_to_par_code(halfword cmd, halfword index) {
3908 switch (cmd) {
3909 case internal_integer_cmd:
3910 switch (index) {
3911 case hang_after_code : return par_hang_after_code;
3912 case adjust_spacing_code : return par_adjust_spacing_code;
3913 case protrude_chars_code : return par_protrude_chars_code;
3914 case pre_tolerance_code : return par_pre_tolerance_code;
3915 case tolerance_code : return par_tolerance_code;
3916 case looseness_code : return par_looseness_code;
3917 case last_line_fit_code : return par_last_line_fit_code;
3918 case line_penalty_code : return par_line_penalty_code;
3919 case inter_line_penalty_code : return par_inter_line_penalty_code;
3920 case club_penalty_code : return par_club_penalty_code;
3921 case widow_penalty_code : return par_widow_penalty_code;
3922 case display_widow_penalty_code : return par_display_widow_penalty_code;
3923 case orphan_penalty_code : return par_orphan_penalty_code;
3924 case single_line_penalty_code : return par_single_line_penalty_code;
3925 case broken_penalty_code : return par_broken_penalty_code;
3926 case adj_demerits_code : return par_adj_demerits_code;
3927 case double_adj_demerits_code : return par_double_adj_demerits_code;
3928 case double_hyphen_demerits_code : return par_double_hyphen_demerits_code;
3929 case final_hyphen_demerits_code : return par_final_hyphen_demerits_code;
3930 case shaping_penalties_mode_code : return par_shaping_penalties_mode_code;
3931 case shaping_penalty_code : return par_shaping_penalty_code;
3932 }
3933 break;
3934 case internal_dimension_cmd:
3935 switch (index) {
3936 case hsize_code : return par_hsize_code;
3937 case hang_indent_code : return par_hang_indent_code;
3938 case par_indent_code : return par_par_indent_code;
3939 case emergency_stretch_code : return par_emergency_stretch_code;
3940 case line_skip_limit_code : return par_line_skip_limit_code;
3941 case emergency_extra_stretch_code : return par_emergency_extra_stretch_code;
3942 }
3943 break;
3944 case internal_glue_cmd:
3945 switch (index) {
3946 case left_skip_code : return par_left_skip_code;
3947 case right_skip_code : return par_right_skip_code;
3948 case par_fill_left_skip_code : return par_par_fill_left_skip_code;
3949 case par_fill_right_skip_code : return par_par_fill_right_skip_code;
3950 case par_init_left_skip_code : return par_par_init_left_skip_code;
3951 case par_init_right_skip_code : return par_par_init_right_skip_code;
3952 case emergency_left_skip_code : return par_emergency_left_skip_code;
3953 case emergency_right_skip_code : return par_emergency_right_skip_code;
3954 case baseline_skip_code : return par_baseline_skip_code;
3955 case line_skip_code : return par_line_skip_code;
3956 }
3957 break;
3958 case specification_reference_cmd:
3959 switch (index) {
3960 case par_shape_code : return par_par_shape_code;
3961 case inter_line_penalties_code : return par_inter_line_penalties_code;
3962 case club_penalties_code : return par_club_penalties_code;
3963 case widow_penalties_code : return par_widow_penalties_code;
3964 case display_widow_penalties_code: return par_display_widow_penalties_code;
3965 case orphan_penalties_code : return par_orphan_penalties_code;
3966 case par_passes_code : return par_par_passes_code;
3967 }
3968 break;
3969 }
3970 return -1;
3971}
3972
3973void tex_update_par_par(halfword cmd, halfword index)
3974{
3975 halfword code = tex_aux_internal_to_par_code(cmd, index);
3976 if (code >= 0) {
3977 halfword par = tex_find_par_par(cur_list.head);
3978 if (par) {
3979 tex_snapshot_par(par, code);
3980 }
3981 }
3982}
3983
3984halfword tex_get_par_par(halfword p, halfword what)
3985{
3986 int set = tex_par_state_is_set(p, what);
3987 switch (what) {
3988 case par_par_shape_code: return set ? par_par_shape(p) : par_shape_par;
3989 case par_inter_line_penalties_code: return set ? par_inter_line_penalties(p) : inter_line_penalties_par;
3990 case par_club_penalties_code: return set ? par_club_penalties(p) : club_penalties_par;
3991 case par_widow_penalties_code: return set ? par_widow_penalties(p) : widow_penalties_par;
3992 case par_display_widow_penalties_code: return set ? par_display_widow_penalties(p) : display_widow_penalties_par;
3993 case par_orphan_penalties_code: return set ? par_orphan_penalties(p) : orphan_penalties_par;
3994 case par_hang_indent_code: return set ? par_hang_indent(p) : hang_indent_par;
3995 case par_hang_after_code: return set ? par_hang_after(p) : hang_after_par;
3996 case par_hsize_code: return set ? par_hsize(p) : hsize_par;
3997 case par_left_skip_code: return set ? par_left_skip(p) : left_skip_par;
3998 case par_right_skip_code: return set ? par_right_skip(p) : right_skip_par;
3999 case par_last_line_fit_code: return set ? par_last_line_fit(p) : last_line_fit_par;
4000 case par_pre_tolerance_code: return set ? par_pre_tolerance(p) : pre_tolerance_par;
4001 case par_tolerance_code: return set ? par_tolerance(p) : tolerance_par;
4002 case par_looseness_code: return set ? par_looseness(p) : looseness_par;
4003 case par_adjust_spacing_code: return set ? par_adjust_spacing(p) : adjust_spacing_par;
4004 case par_adj_demerits_code: return set ? par_adj_demerits(p) : adj_demerits_par;
4005 case par_double_adj_demerits_code: return set ? par_double_adj_demerits(p) : double_adj_demerits_par;
4006 case par_protrude_chars_code: return set ? par_protrude_chars(p) : protrude_chars_par;
4007 case par_line_penalty_code: return set ? par_line_penalty(p) : line_penalty_par;
4008 case par_double_hyphen_demerits_code: return set ? par_double_hyphen_demerits(p) : double_hyphen_demerits_par;
4009 case par_final_hyphen_demerits_code: return set ? par_final_hyphen_demerits(p) : final_hyphen_demerits_par;
4010 case par_inter_line_penalty_code: return set ? par_inter_line_penalty(p) : inter_line_penalty_par;
4011 case par_club_penalty_code: return set ? par_club_penalty(p) : club_penalty_par;
4012 case par_widow_penalty_code: return set ? par_widow_penalty(p) : widow_penalty_par;
4013 case par_display_widow_penalty_code: return set ? par_display_widow_penalty(p) : display_widow_penalty_par;
4014 case par_orphan_penalty_code: return set ? par_orphan_penalty(p) : orphan_penalty_par;
4015 case par_single_line_penalty_code: return set ? par_single_line_penalty(p) : single_line_penalty_par;
4016 case par_broken_penalty_code: return set ? par_broken_penalty(p) : broken_penalty_par;
4017 case par_emergency_stretch_code: return set ? par_emergency_stretch(p) : emergency_stretch_par;
4018 case par_par_indent_code: return set ? par_par_indent(p) : par_indent_par;
4019 case par_par_fill_left_skip_code: return set ? par_par_fill_left_skip(p) : par_fill_left_skip_par;
4020 case par_par_fill_right_skip_code: return set ? par_par_fill_right_skip(p) : par_fill_right_skip_par;
4021 case par_par_init_left_skip_code: return set ? par_par_init_left_skip(p) : par_init_left_skip_par;
4022 case par_par_init_right_skip_code: return set ? par_par_init_right_skip(p) : par_init_right_skip_par;
4023 case par_emergency_left_skip_code: return set ? par_emergency_left_skip(p) : emergency_left_skip_par;
4024 case par_emergency_right_skip_code: return set ? par_emergency_right_skip(p) : emergency_right_skip_par;
4025 case par_baseline_skip_code: return set ? par_baseline_skip(p) : baseline_skip_par;
4026 case par_line_skip_code: return set ? par_line_skip(p) : line_skip_par;
4027 case par_line_skip_limit_code: return set ? par_line_skip_limit(p) : line_skip_limit_par;
4028 case par_adjust_spacing_step_code: return set ? par_adjust_spacing_step(p) : adjust_spacing_step_par;
4029 case par_adjust_spacing_shrink_code: return set ? par_adjust_spacing_shrink(p) : adjust_spacing_shrink_par;
4030 case par_adjust_spacing_stretch_code: return set ? par_adjust_spacing_stretch(p) : adjust_spacing_stretch_par;
4031 case par_hyphenation_mode_code: return set ? par_hyphenation_mode(p) : hyphenation_mode_par;
4032 case par_shaping_penalties_mode_code: return set ? par_shaping_penalties_mode(p) : shaping_penalties_mode_par;
4033 case par_shaping_penalty_code: return set ? par_shaping_penalty(p) : shaping_penalty_par;
4034 case par_emergency_extra_stretch_code: return set ? par_emergency_extra_stretch(p) : emergency_extra_stretch_par;
4035 case par_par_passes_code: return set ? par_par_passes(p) : par_passes_par;
4036 }
4037 return null;
4038}
4039
4040void tex_set_par_par(halfword p, halfword what, halfword v, int force)
4041{
4042 if (force || tex_par_state_is_set(p, what)) {
4043 switch (what) {
4044 case par_hsize_code:
4045 par_hsize(p) = v;
4046 break;
4047 case par_left_skip_code:
4048 if (par_left_skip(p)) {
4049 tex_flush_node(par_left_skip(p));
4050 }
4051 par_left_skip(p) = v ? tex_copy_node(v) : null;
4052 break;
4053 case par_right_skip_code:
4054 if (par_right_skip(p)) {
4055 tex_flush_node(par_right_skip(p));
4056 }
4057 par_right_skip(p) = v ? tex_copy_node(v) : null;
4058 break;
4059 case par_hang_indent_code:
4060 par_hang_indent(p) = v;
4061 break;
4062 case par_hang_after_code:
4063 par_hang_after(p) = v;
4064 break;
4065 case par_par_indent_code:
4066 par_par_indent(p) = v;
4067 break;
4068 case par_par_fill_left_skip_code:
4069 if (par_par_fill_left_skip(p)) {
4070 tex_flush_node(par_par_fill_left_skip(p));
4071 }
4072 par_par_fill_left_skip(p) = v ? tex_copy_node(v) : null;
4073 break;
4074 case par_par_fill_right_skip_code:
4075 if (par_par_fill_right_skip(p)) {
4076 tex_flush_node(par_par_fill_right_skip(p));
4077 }
4078 par_par_fill_right_skip(p) = v ? tex_copy_node(v) : null;
4079 break;
4080 case par_par_init_left_skip_code:
4081 if (par_par_init_left_skip(p)) {
4082 tex_flush_node(par_par_init_left_skip(p));
4083 }
4084 par_par_init_left_skip(p) = v ? tex_copy_node(v) : null;
4085 break;
4086 case par_par_init_right_skip_code:
4087 if (par_par_init_right_skip(p)) {
4088 tex_flush_node(par_par_init_right_skip(p));
4089 }
4090 par_par_init_right_skip(p) = v ? tex_copy_node(v) : null;
4091 break;
4092 case par_emergency_left_skip_code:
4093 if (par_emergency_left_skip(p)) {
4094 tex_flush_node(par_emergency_left_skip(p));
4095 }
4096 par_emergency_left_skip(p) = v ? tex_copy_node(v) : null;
4097 break;
4098 case par_emergency_right_skip_code:
4099 if (par_emergency_right_skip(p)) {
4100 tex_flush_node(par_emergency_right_skip(p));
4101 }
4102 par_emergency_right_skip(p) = v ? tex_copy_node(v) : null;
4103 break;
4104 case par_adjust_spacing_code:
4105 par_adjust_spacing(p) = v;
4106 break;
4107 case par_protrude_chars_code:
4108 par_protrude_chars(p) = v;
4109 break;
4110 case par_pre_tolerance_code:
4111 par_pre_tolerance(p) = v;
4112 break;
4113 case par_tolerance_code:
4114 par_tolerance(p) = v;
4115 break;
4116 case par_emergency_stretch_code:
4117 par_emergency_stretch(p) = v;
4118 break;
4119 case par_looseness_code:
4120 par_looseness(p) = v;
4121 break;
4122 case par_single_line_penalty_code:
4123 par_single_line_penalty(p) = v;
4124 break;
4125 case par_last_line_fit_code:
4126 par_last_line_fit(p) = v;
4127 break;
4128 case par_line_penalty_code:
4129 par_line_penalty(p) = v;
4130 break;
4131 case par_inter_line_penalty_code:
4132 par_inter_line_penalty(p) = v;
4133 break;
4134 case par_club_penalty_code:
4135 par_club_penalty(p) = v;
4136 break;
4137 case par_widow_penalty_code:
4138 par_widow_penalty(p) = v;
4139 break;
4140 case par_display_widow_penalty_code:
4141 par_display_widow_penalty(p) = v;
4142 break;
4143 case par_orphan_penalty_code:
4144 par_orphan_penalty(p) = v;
4145 break;
4146 case par_broken_penalty_code:
4147 par_broken_penalty(p) = v;
4148 break;
4149 case par_adj_demerits_code:
4150 par_adj_demerits(p) = v;
4151 break;
4152 case par_double_adj_demerits_code:
4153 par_double_adj_demerits(p) = v;
4154 break;
4155 case par_double_hyphen_demerits_code:
4156 par_double_hyphen_demerits(p) = v;
4157 break;
4158 case par_final_hyphen_demerits_code:
4159 par_final_hyphen_demerits(p) = v;
4160 break;
4161 case par_par_shape_code:
4162 if (par_par_shape(p)) {
4163 tex_flush_node(par_par_shape(p));
4164 }
4165 par_par_shape(p) = v ? tex_copy_node(v) : null;
4166 break;
4167 case par_inter_line_penalties_code:
4168 if (par_inter_line_penalties(p)) {
4169 tex_flush_node(par_inter_line_penalties(p));
4170 }
4171 par_inter_line_penalties(p) = v ? tex_copy_node(v) : null;
4172 break;
4173 case par_club_penalties_code:
4174 if (par_club_penalties(p)) {
4175 tex_flush_node(par_club_penalties(p));
4176 }
4177 par_club_penalties(p) = v ? tex_copy_node(v) : null;
4178 break;
4179 case par_widow_penalties_code:
4180 if (par_widow_penalties(p)) {
4181 tex_flush_node(par_widow_penalties(p));
4182 }
4183 par_widow_penalties(p) = v ? tex_copy_node(v) : null;
4184 break;
4185 case par_display_widow_penalties_code:
4186 if (par_display_widow_penalties(p)) {
4187 tex_flush_node(par_display_widow_penalties(p));
4188 }
4189 par_display_widow_penalties(p) = v ? tex_copy_node(v) : null;
4190 break;
4191 case par_orphan_penalties_code:
4192 if (par_orphan_penalties(p)) {
4193 tex_flush_node(par_orphan_penalties(p));
4194 }
4195 par_orphan_penalties(p) = v ? tex_copy_node(v) : null;
4196 break;
4197 case par_baseline_skip_code:
4198 if (par_baseline_skip(p)) {
4199 tex_flush_node(par_baseline_skip(p));
4200 }
4201 par_baseline_skip(p) = v ? tex_copy_node(v) : null;
4202 break;
4203 case par_line_skip_code:
4204 if (par_line_skip(p)) {
4205 tex_flush_node(par_line_skip(p));
4206 }
4207 par_line_skip(p) = v ? tex_copy_node(v) : null;
4208 break;
4209 case par_line_skip_limit_code:
4210 par_line_skip_limit(p) = v;
4211 break;
4212 case par_adjust_spacing_step_code:
4213 par_adjust_spacing_step(p) = v;
4214 break;
4215 case par_adjust_spacing_shrink_code:
4216 par_adjust_spacing_shrink(p) = v;
4217 break;
4218 case par_adjust_spacing_stretch_code:
4219 par_adjust_spacing_stretch(p) = v;
4220 break;
4221 case par_hyphenation_mode_code:
4222 par_hyphenation_mode(p) = v;
4223 break;
4224 case par_shaping_penalties_mode_code:
4225 par_shaping_penalties_mode(p) = v;
4226 break;
4227 case par_shaping_penalty_code:
4228 par_shaping_penalty(p) = v;
4229 break;
4230 case par_emergency_extra_stretch_code:
4231 par_emergency_extra_stretch(p) = v;
4232 break;
4233 case par_par_passes_code:
4234 if (par_par_passes(p)) {
4235 tex_flush_node(par_par_passes(p));
4236 }
4237 par_par_passes(p) = v ? tex_copy_node(v) : null;
4238 break;
4239 }
4240 tex_set_par_state(p, what);
4241 }
4242}
4243
4244
4248
4249
4320
4321void tex_snapshot_par(halfword p, halfword what)
4322{
4323 if (p && lmt_main_state.run_state != initializing_state) {
4324 int unset = 0;
4325 if (what) {
4326 if (what < 0) {
4327 unset = 1;
4328 what = -what;
4329 }
4330 if (what > par_all_category) {
4331 what = par_all_category;
4332 }
4333 } else {
4334 unset = 1;
4335 what = par_all_category;
4336 }
4337 if (tex_par_to_be_set(what, par_hsize_code)) {
4338 par_hsize(p) = unset ? null : hsize_par;
4339 }
4340 if (tex_par_to_be_set(what, par_left_skip_code)) {
4341 halfword v = unset ? null : left_skip_par;
4342 if (par_left_skip(p)) {
4343 tex_flush_node(par_left_skip(p));
4344 }
4345 par_left_skip(p) = v ? tex_copy_node(v) : null;
4346 }
4347 if (tex_par_to_be_set(what, par_right_skip_code)) {
4348 halfword v = unset ? null : right_skip_par;
4349 if (par_right_skip(p)) {
4350 tex_flush_node(par_right_skip(p));
4351 }
4352 par_right_skip(p) = v ? tex_copy_node(v) : null;
4353 }
4354 if (tex_par_to_be_set(what, par_hang_indent_code)) {
4355 par_hang_indent(p) = unset ? null : hang_indent_par;
4356 }
4357 if (tex_par_to_be_set(what, par_hang_after_code)) {
4358 par_hang_after(p) = unset ? null : hang_after_par;
4359 }
4360 if (tex_par_to_be_set(what, par_par_indent_code)) {
4361 par_par_indent(p) = unset ? null : par_indent_par;
4362 }
4363 if (tex_par_to_be_set(what, par_par_fill_left_skip_code)) {
4364 halfword v = unset ? null : par_fill_left_skip_par;
4365 if (par_par_fill_left_skip(p)) {
4366 tex_flush_node(par_par_fill_left_skip(p));
4367 }
4368 par_par_fill_left_skip(p) = v ? tex_copy_node(v) : null;
4369 }
4370 if (tex_par_to_be_set(what, par_par_fill_right_skip_code)) {
4371 halfword v = unset ? null : par_fill_right_skip_par;
4372 if (par_par_fill_right_skip(p)) {
4373 tex_flush_node(par_par_fill_right_skip(p));
4374 }
4375 par_par_fill_right_skip(p) = v ? tex_copy_node(v) : null;
4376 }
4377 if (tex_par_to_be_set(what, par_par_init_left_skip_code)) {
4378 halfword v = unset ? null : par_init_left_skip_par;
4379 if (par_par_init_left_skip(p)) {
4380 tex_flush_node(par_par_init_left_skip(p));
4381 }
4382 par_par_init_left_skip(p) = v ? tex_copy_node(v) : null;
4383 }
4384 if (tex_par_to_be_set(what, par_par_init_right_skip_code)) {
4385 halfword v = unset ? null : par_init_right_skip_par;
4386 if (par_par_init_right_skip(p)) {
4387 tex_flush_node(par_par_init_right_skip(p));
4388 }
4389 par_par_init_right_skip(p) = v ? tex_copy_node(v) : null;
4390 }
4391 if (tex_par_to_be_set(what, par_emergency_left_skip_code)) {
4392 halfword v = unset ? null : emergency_left_skip_par;
4393 if (par_emergency_left_skip(p)) {
4394 tex_flush_node(par_emergency_left_skip(p));
4395 }
4396 par_emergency_left_skip(p) = v ? tex_copy_node(v) : null;
4397 }
4398 if (tex_par_to_be_set(what, par_emergency_right_skip_code)) {
4399 halfword v = unset ? null : emergency_right_skip_par;
4400 if (par_emergency_right_skip(p)) {
4401 tex_flush_node(par_emergency_right_skip(p));
4402 }
4403 par_emergency_right_skip(p) = v ? tex_copy_node(v) : null;
4404 }
4405 if (tex_par_to_be_set(what, par_adjust_spacing_code)) {
4406 par_adjust_spacing(p) = unset ? null : adjust_spacing_par;
4407 }
4408 if (tex_par_to_be_set(what, par_protrude_chars_code)) {
4409 par_protrude_chars(p) = unset ? null : protrude_chars_par;
4410 }
4411 if (tex_par_to_be_set(what, par_pre_tolerance_code)) {
4412 par_pre_tolerance(p) = unset ? null : pre_tolerance_par;
4413 }
4414 if (tex_par_to_be_set(what, par_tolerance_code)) {
4415 par_tolerance(p) = unset ? null : tolerance_par;
4416 }
4417 if (tex_par_to_be_set(what, par_emergency_stretch_code)) {
4418 par_emergency_stretch(p) = unset ? null : emergency_stretch_par;
4419 }
4420 if (tex_par_to_be_set(what, par_looseness_code)) {
4421 par_looseness(p) = unset ? null : looseness_par;
4422 }
4423 if (tex_par_to_be_set(what, par_last_line_fit_code)) {
4424 par_last_line_fit(p) = unset ? null : last_line_fit_par;
4425 }
4426 if (tex_par_to_be_set(what, par_line_penalty_code)) {
4427 par_line_penalty(p) = unset ? null : line_penalty_par;
4428 }
4429 if (tex_par_to_be_set(what, par_inter_line_penalty_code)) {
4430 par_inter_line_penalty(p) = unset ? null : inter_line_penalty_par;
4431 }
4432 if (tex_par_to_be_set(what, par_club_penalty_code)) {
4433 par_club_penalty(p) = unset ? null : club_penalty_par;
4434 }
4435 if (tex_par_to_be_set(what, par_widow_penalty_code)) {
4436 par_widow_penalty(p) = unset ? null : widow_penalty_par;
4437 }
4438 if (tex_par_to_be_set(what, par_display_widow_penalty_code)) {
4439 par_display_widow_penalty(p) = unset ? null : display_widow_penalty_par;
4440 }
4441 if (tex_par_to_be_set(what, par_orphan_penalty_code)) {
4442 par_orphan_penalty(p) = unset ? null : orphan_penalty_par;
4443 }
4444 if (tex_par_to_be_set(what, par_single_line_penalty_code)) {
4445 par_single_line_penalty(p) = unset ? null : single_line_penalty_par;
4446 }
4447 if (tex_par_to_be_set(what, par_broken_penalty_code)) {
4448 par_broken_penalty(p) = unset ? null : broken_penalty_par;
4449 }
4450 if (tex_par_to_be_set(what, par_adj_demerits_code)) {
4451 par_adj_demerits(p) = unset ? null : adj_demerits_par;
4452 }
4453 if (tex_par_to_be_set(what, par_double_adj_demerits_code)) {
4454 par_double_adj_demerits(p) = unset ? null : double_adj_demerits_par;
4455 }
4456 if (tex_par_to_be_set(what, par_double_hyphen_demerits_code)){
4457 par_double_hyphen_demerits(p) = unset ? null : double_hyphen_demerits_par;
4458 }
4459 if (tex_par_to_be_set(what, par_final_hyphen_demerits_code)) {
4460 par_final_hyphen_demerits(p) = unset ? null : final_hyphen_demerits_par;
4461 }
4462 if (tex_par_to_be_set(what, par_par_shape_code)) {
4463 halfword v = unset ? null : par_shape_par;
4464 if (par_par_shape(p)) {
4465 tex_flush_node(par_par_shape(p));
4466 }
4467 par_par_shape(p) = v ? tex_copy_node(v) : null;
4468 }
4469 if (tex_par_to_be_set(what, par_inter_line_penalties_code)) {
4470 halfword v = unset ? null : inter_line_penalties_par;
4471 if (par_inter_line_penalties(p)) {
4472 tex_flush_node(par_inter_line_penalties(p));
4473 }
4474 par_inter_line_penalties(p) = v ? tex_copy_node(v) : null;
4475 }
4476 if (tex_par_to_be_set(what, par_club_penalties_code)) {
4477 halfword v = unset ? null : club_penalties_par;
4478 if (par_club_penalties(p)) {
4479 tex_flush_node(par_club_penalties(p));
4480 }
4481 par_club_penalties(p) = v ? tex_copy_node(v) : null;
4482 }
4483 if (tex_par_to_be_set(what, par_widow_penalties_code)) {
4484 halfword v = unset ? null : widow_penalties_par;
4485 if (par_widow_penalties(p)) {
4486 tex_flush_node(par_widow_penalties(p));
4487 }
4488 par_widow_penalties(p) = v ? tex_copy_node(v) : null;
4489 }
4490 if (tex_par_to_be_set(what, par_display_widow_penalties_code)) {
4491 halfword v = unset ? null : display_widow_penalties_par;
4492 if (par_display_widow_penalties(p)) {
4493 tex_flush_node(par_display_widow_penalties(p));
4494 }
4495 par_display_widow_penalties(p) = v ? tex_copy_node(v) : null;
4496 }
4497 if (tex_par_to_be_set(what, par_orphan_penalties_code)) {
4498 halfword v = unset ? null : orphan_penalties_par;
4499 if (par_orphan_penalties(p)) {
4500 tex_flush_node(par_orphan_penalties(p));
4501 }
4502 par_orphan_penalties(p) = v ? tex_copy_node(v) : null;
4503 }
4504 if (tex_par_to_be_set(what, par_baseline_skip_code)) {
4505 halfword v = unset ? null : baseline_skip_par;
4506 if (par_baseline_skip(p)) {
4507 tex_flush_node(par_baseline_skip(p));
4508 }
4509 par_baseline_skip(p) = v ? tex_copy_node(v) : null;
4510 }
4511 if (tex_par_to_be_set(what, par_line_skip_code)) {
4512 halfword v = unset ? null : line_skip_par;
4513 if (par_line_skip(p)) {
4514 tex_flush_node(par_line_skip(p));
4515 }
4516 par_line_skip(p) = v ? tex_copy_node(v) : null;
4517 }
4518 if (tex_par_to_be_set(what, par_line_skip_limit_code)) {
4519 par_line_skip_limit(p) = unset ? null : line_skip_limit_par;
4520 }
4521 if (tex_par_to_be_set(what, par_adjust_spacing_step_code)) {
4522 par_adjust_spacing_step(p) = unset ? null : adjust_spacing_step_par;
4523 }
4524 if (tex_par_to_be_set(what, par_adjust_spacing_shrink_code)) {
4525 par_adjust_spacing_shrink(p) = unset ? null : adjust_spacing_shrink_par;
4526 }
4527 if (tex_par_to_be_set(what, par_adjust_spacing_stretch_code)) {
4528 par_adjust_spacing_stretch(p) = unset ? null : adjust_spacing_stretch_par;
4529 }
4530 if (tex_par_to_be_set(what, par_hyphenation_mode_code)) {
4531 par_hyphenation_mode(p) = unset ? null : hyphenation_mode_par;
4532 }
4533 if (tex_par_to_be_set(what, par_shaping_penalties_mode_code)) {
4534 par_shaping_penalties_mode(p) = unset ? null : shaping_penalties_mode_par;
4535 }
4536 if (tex_par_to_be_set(what, par_shaping_penalty_code)) {
4537 par_shaping_penalty(p) = unset ? null : shaping_penalty_par;
4538 }
4539 if (tex_par_to_be_set(what, par_emergency_extra_stretch_code)) {
4540 par_emergency_extra_stretch(p) = unset ? null : emergency_extra_stretch_par;
4541 }
4542 if (tex_par_to_be_set(what, par_par_passes_code)) {
4543 halfword v = unset ? null : par_passes_par;
4544 if (par_par_passes(p)) {
4545 tex_flush_node(par_par_passes(p));
4546 }
4547 par_par_passes(p) = v ? tex_copy_node(v) : null;
4548 }
4549 if (tex_par_to_be_set(what, par_single_line_penalty_code)) {
4550 par_single_line_penalty(p) = unset ? null : single_line_penalty_par;
4551 }
4552
4553 if (what == par_all_category) {
4554 par_state(p) = unset ? 0 : par_all_category;
4555 } else if (unset) {
4556 par_state(p) &= ~(what | par_state(p));
4557 } else {
4558 par_state(p) |= what;
4559 }
4560 }
4561}
4562
4563halfword tex_find_par_par(halfword head)
4564{
4565 if (head) {
4566 if (node_type(head) == temp_node) {
4567 head = node_next(head);
4568 }
4569 if (head && node_type(head) == par_node) {
4570 return head;
4571 }
4572 }
4573 return null;
4574}
4575
4576halfword tex_reversed_node_list(halfword list)
4577{
4578 if (list) {
4579 halfword prev = list;
4580 halfword last = list;
4581 halfword next = node_next(list);
4582 if (next) {
4583 while (1) {
4584 tex_couple_nodes(list, prev);
4585 if (node_type(list) == dir_node) {
4586 node_subtype(list) = node_subtype(list) == cancel_dir_subtype ? normal_dir_subtype : cancel_dir_subtype;
4587 }
4588 if (next) {
4589 prev = list;
4590 list = next;
4591 next = node_next(list);
4592 } else {
4593 node_next(last) = null;
4594 node_prev(list) = null;
4595 return list;
4596 }
4597 }
4598 }
4599 }
4600 return list;
4601}
4602
4603
4604
4605halfword tex_new_specification_node(halfword n, quarterword s, halfword options)
4606{
4607 halfword p = tex_new_node(specification_node, s);
4608 tex_new_specification_list(p, n, options);
4609 return p;
4610}
4611
4612void tex_dispose_specification_nodes(void) {
4613 if (par_shape_par) { tex_flush_node(par_shape_par); par_shape_par = null; }
4614 if (par_passes_par) { tex_flush_node(par_passes_par); par_passes_par = null; }
4615 if (inter_line_penalties_par) { tex_flush_node(inter_line_penalties_par); inter_line_penalties_par = null; }
4616 if (club_penalties_par) { tex_flush_node(club_penalties_par); club_penalties_par = null; }
4617 if (widow_penalties_par) { tex_flush_node(widow_penalties_par); widow_penalties_par = null; }
4618 if (display_widow_penalties_par) { tex_flush_node(display_widow_penalties_par); display_widow_penalties_par = null; }
4619 if (math_forward_penalties_par) { tex_flush_node(math_forward_penalties_par); math_forward_penalties_par = null; }
4620 if (math_backward_penalties_par) { tex_flush_node(math_backward_penalties_par); math_backward_penalties_par = null; }
4621 if (orphan_penalties_par) { tex_flush_node(orphan_penalties_par); orphan_penalties_par = null; }
4622}
4623
4624void tex_null_specification_list(halfword a)
4625{
4626 specification_pointer(a) = NULL;
4627 specification_count(a) = 0;
4628}
4629
4630static void *tex_aux_allocate_specification(halfword p, int n, size_t *s)
4631{
4632 void *l = NULL;
4633 if (node_subtype(p) == par_passes_code) {
4634 n *= par_passes_size;
4635 }
4636 *s = n * sizeof(memoryword);
4637 lmt_node_memory_state.extra_data.allocated += (int) *s;
4638 lmt_node_memory_state.extra_data.ptr = lmt_node_memory_state.extra_data.allocated;
4639 if (lmt_node_memory_state.extra_data.ptr > lmt_node_memory_state.extra_data.top) {
4640 lmt_node_memory_state.extra_data.top = lmt_node_memory_state.extra_data.ptr;
4641 }
4642 l = lmt_memory_calloc(n, sizeof(memoryword));
4643 if (! l) {
4644 tex_overflow_error("nodes", (int) *s);
4645 }
4646 return l;
4647}
4648
4649static void tex_aux_deallocate_specification(void *p, int n)
4650{
4651 size_t s = n * sizeof(memoryword);
4652 lmt_node_memory_state.extra_data.allocated -= (int) s;
4653 lmt_node_memory_state.extra_data.ptr = lmt_node_memory_state.extra_data.allocated;
4654 lmt_memory_free(p);
4655}
4656
4657void tex_new_specification_list(halfword a, halfword n, halfword o)
4658{
4659 size_t size = 0;
4660 specification_pointer(a) = tex_aux_allocate_specification(a, n, &size);
4661 specification_count(a) = specification_pointer(a) ? n : 0;
4662 specification_options(a) = o;
4663 if (node_subtype(a) == par_passes_code) {
4664 for (int i = 1; i <= n; i++) {
4665 tex_set_passes_threshold(a, i, max_dimension);
4666 tex_set_passes_badness(a, i, infinite_bad);
4667 tex_set_passes_optional(a, i, 0x1000000);
4668 }
4669 }
4670}
4671
4672void tex_dispose_specification_list(halfword a)
4673{
4674 if (specification_pointer(a)) {
4675 tex_aux_deallocate_specification(specification_pointer(a), specification_count(a));
4676 specification_pointer(a) = NULL;
4677 specification_count(a) = 0;
4678 specification_options(a) = 0;
4679 }
4680}
4681
4682void tex_copy_specification_list(halfword a, halfword b) {
4683 if (specification_pointer(b)) {
4684 size_t size = 0;
4685 specification_pointer(a) = tex_aux_allocate_specification(b, specification_count(b), &size);
4686 if (specification_pointer(a) && specification_pointer(b)) {
4687 specification_count(a) = specification_count(b);
4688 specification_options(a) = specification_options(b);
4689 memcpy(specification_pointer(a), specification_pointer(b), size);
4690 } else {
4691 specification_count(a) = 0;
4692 specification_options(a) = 0;
4693 }
4694 }
4695}
4696
4697void tex_shift_specification_list(halfword a, int n, int rotate)
4698{
4699 if (specification_pointer(a)) {
4700 halfword c = specification_count(a);
4701 if (rotate) {
4702 if (n > 0 && c > 0 && n < c && c != n) {
4703 size_t s = 0;
4704 memoryword *b = tex_aux_allocate_specification(a, c, &s);
4705 memoryword *p = specification_pointer(a);
4706 halfword m = c - n;
4707 s = m * sizeof(memoryword);
4708 memcpy(b, p + n, s);
4709 s = n * sizeof(memoryword);
4710 memcpy(b + m, p, s);
4711 tex_aux_deallocate_specification(specification_pointer(a), c);
4712 specification_pointer(a) = b;
4713 }
4714 } else {
4715
4716 if (n > 0) {
4717 halfword o = 0;
4718 halfword m = 0;
4719 memoryword *b = NULL;
4720 if (n > 0 && c > 0 && n < c) {
4721 size_t s = 0;
4722 memoryword *p = specification_pointer(a);
4723 o = specification_options(a);
4724 m = c - n;
4725 b = tex_aux_allocate_specification(a, m, &s);
4726 memcpy(b, p + n, s);
4727 }
4728 if (c > 0) {
4729 tex_aux_deallocate_specification(specification_pointer(a), c);
4730 }
4731 specification_pointer(a) = b;
4732 specification_count(a) = m;
4733 specification_options(a) = o;
4734 }
4735 }
4736 }
4737}
4738
4739
4740
4741void tex_set_disc_field(halfword target, halfword location, halfword source)
4742{
4743 switch (location) {
4744 case pre_break_code: target = disc_pre_break(target); break;
4745 case post_break_code: target = disc_post_break(target); break;
4746 case no_break_code: target = disc_no_break(target); break;
4747 }
4748 node_prev(source) = null;
4749 if (source) {
4750 node_head(target) = source;
4751 node_tail(target) = tex_tail_of_node_list(source);
4752 } else {
4753 node_head(target) = null;
4754 node_tail(target) = null;
4755 }
4756}
4757
4758void tex_check_disc_field(halfword n)
4759{
4760 halfword p = disc_pre_break_head(n);
4761 disc_pre_break_tail(n) = p ? tex_tail_of_node_list(p) : null;
4762 p = disc_post_break_head(n);
4763 disc_post_break_tail(n) = p ? tex_tail_of_node_list(p) : null;
4764 p = disc_no_break_head(n);
4765 disc_no_break_tail(n) = p ? tex_tail_of_node_list(p) : null;
4766}
4767
4768void tex_set_discpart(halfword d, halfword h, halfword t, halfword code)
4769{
4770 halfword c = h;
4771 switch (node_subtype(d)) {
4772 case automatic_discretionary_code:
4773 case mathematics_discretionary_code:
4774 code = glyph_discpart_always;
4775 break;
4776 }
4777 while (c) {
4778 if (node_type(c) == glyph_node) {
4779 set_glyph_discpart(c, code);
4780 }
4781 if (c == t) {
4782 break;
4783 } else {
4784 c = node_next(c);
4785 }
4786 }
4787}
4788
4789halfword tex_flatten_discretionaries(halfword head, int *count, int nest)
4790{
4791 halfword current = head;
4792 while (current) {
4793 halfword next = node_next(current);
4794 switch (node_type(current)) {
4795 case disc_node:
4796 {
4797 halfword d = current;
4798 halfword h = disc_no_break_head(d);
4799 halfword t = disc_no_break_tail(d);
4800 if (h) {
4801 tex_set_discpart(current, h, t, glyph_discpart_replace);
4802 tex_try_couple_nodes(t, next);
4803 if (current == head) {
4804 head = h;
4805 } else {
4806 tex_try_couple_nodes(node_prev(current), h);
4807 }
4808 disc_no_break_head(d) = null;
4809 } else if (current == head) {
4810 head = next;
4811 } else {
4812 tex_try_couple_nodes(node_prev(current), next);
4813 }
4814 tex_flush_node(d);
4815 if (count) {
4816 *count += 1;
4817 }
4818 break;
4819 }
4820 case hlist_node:
4821 case vlist_node:
4822 if (nest) {
4823 halfword list = box_list(current);
4824 if (list) {
4825 box_list(current) = tex_flatten_discretionaries(list, count, nest);
4826 }
4827 }
4828 break;
4829 }
4830 current = next;
4831 }
4832 return head;
4833}
4834
4835int tex_flatten_leaders(halfword box, int grp, int just_pack)
4836{
4837 halfword head = box ? box_list(box) : null;
4838 if (head) {
4839 halfword current = head;
4840 int count = 0;
4841 while (current) {
4842 halfword next = node_next(current);
4843 if (node_type(current) == glue_node && node_subtype(current) == u_leaders) {
4844 halfword prev = node_prev(current);
4845 halfword leader = glue_leader_ptr(current);
4846 if (leader && (node_type(leader) == hlist_node || node_type(leader) == vlist_node)) {
4847 halfword packed = null;
4848 halfword amount = glue_amount(current);
4849 halfword callback = glue_callback(current);
4850 double width = (double) amount;
4851 switch (box_glue_sign(box)) {
4852 case stretching_glue_sign:
4853 if (glue_stretch_order(current) == box_glue_order(box)) {
4854 width += glue_stretch(current) * (double) box_glue_set(box);
4855 }
4856 break;
4857 case shrinking_glue_sign:
4858 if (glue_shrink_order(current) == box_glue_order(box)) {
4859 width -= glue_shrink(current) * (double) box_glue_set(box);
4860 }
4861 break;
4862 }
4863 if (node_type(leader) == hlist_node) {
4864 packed = tex_hpack(box_list(leader), scaledround(width), packing_exactly, box_dir(leader), holding_none_option, box_limit_none);
4865 } else {
4866 packed = tex_vpack(box_list(leader), scaledround(width), packing_exactly, 0, box_dir(leader), holding_none_option, NULL);
4867 }
4868 box_list(leader) = box_list(packed);
4869 box_width(leader) = box_width(packed);
4870 box_height(leader) = box_height(packed);
4871 box_depth(leader) = box_depth(packed);
4872 box_glue_order(leader) = box_glue_order(packed);
4873 box_glue_sign(leader) = box_glue_sign(packed);
4874 box_glue_set(leader) = box_glue_set(packed);
4875 set_box_package_state(leader, package_u_leader_set);
4876 box_list(packed) = null;
4877 tex_flush_node(packed);
4878 glue_leader_ptr(current) = null;
4879 tex_flush_node(current);
4880 if (callback && ! just_pack) {
4881 node_prev(leader) = null;
4882 node_next(leader) = null;
4883 leader = lmt_uleader_callback(leader, grp, callback);
4884 }
4885 tex_try_couple_nodes(leader, next);
4886 if (current == head) {
4887 box_list(box) = leader;
4888 } else {
4889 tex_try_couple_nodes(prev, leader);
4890 }
4891 count += 1;
4892 }
4893 }
4894 current = next;
4895 }
4896 return count;
4897 } else {
4898 return 0;
4899 }
4900}
4901
4902
4907
4908void tex_soften_hyphens(halfword head, int *found, int *replaced)
4909{
4910 halfword current = head;
4911 while (current) {
4912 switch (node_type(current)) {
4913 case glyph_node:
4914 {
4915 if (glyph_character(current) == 0x2D) {
4916
4920 ++(*found);
4921 switch (glyph_discpart(current)) {
4922 case glyph_discpart_unset:
4923
4924 set_glyph_discpart(current, glyph_discpart_always);
4925 case glyph_discpart_always:
4926
4927 break;
4928 default :
4929 if (tex_char_exists(glyph_font(current), 0xAD)) {
4930 ++(*replaced);
4931 glyph_character(current) = 0xAD;
4932 }
4933 break;
4934 }
4935 }
4936 break;
4937 }
4938 case hlist_node:
4939 case vlist_node:
4940 {
4941 halfword list = box_list(current);
4942 if (list) {
4943 tex_soften_hyphens(list, found, replaced);
4944 }
4945 break;
4946 }
4947 }
4948 current = node_next(current);
4949 }
4950}
4951
4952halfword tex_harden_spaces(halfword head, halfword tolerance, int* count)
4953{
4954
4955 (void) tolerance;
4956 (void) count;
4957 return head;
4958}
4959
4960halfword tex_get_special_node_list(special_node_list_types list, halfword *tail)
4961{
4962 halfword h = null;
4963 halfword t = null;
4964 switch (list) {
4965 case page_insert_list_type:
4966 h = node_next(page_insert_head);
4967 if (h == page_insert_head) {
4968 h = null;
4969 }
4970 break;
4971 case contribute_list_type:
4972 h = node_next(contribute_head);
4973 break;
4974 case page_list_type:
4975 h = node_next(page_head);
4976 t = lmt_page_builder_state.page_tail;
4977 break;
4978 case temp_list_type:
4979 h = node_next(temp_head);
4980 break;
4981 case hold_list_type:
4982 h = node_next(hold_head);
4983 break;
4984 case post_adjust_list_type:
4985 h = node_next(post_adjust_head);
4986 t = lmt_packaging_state.post_adjust_tail;
4987 break;
4988 case pre_adjust_list_type:
4989 h = node_next(pre_adjust_head);
4990 t = lmt_packaging_state.pre_adjust_tail;
4991 break;
4992 case post_migrate_list_type:
4993 h = node_next(post_migrate_head);
4994 t = lmt_packaging_state.post_migrate_tail;
4995 break;
4996 case pre_migrate_list_type:
4997 h = node_next(pre_migrate_head);
4998 t = lmt_packaging_state.pre_migrate_tail;
4999 break;
5000 case align_list_type:
5001 h = node_next(align_head);
5002 break;
5003 case page_discards_list_type:
5004 h = lmt_packaging_state.page_discards_head;
5005 break;
5006 case split_discards_list_type:
5007 h = lmt_packaging_state.split_discards_head;
5008 break;
5009 }
5010 node_prev(h) = null;
5011 if (tail) {
5012 *tail = t ? t : (h ? tex_tail_of_node_list(h) : null);
5013 }
5014 return h;
5015};
5016
5017int tex_is_special_node_list(halfword n, int *istail)
5018{
5019 if (istail) {
5020 *istail = 0;
5021 }
5022 if (! n) {
5023 return -1;
5024 } else if (n == node_next(page_insert_head)) {
5025 return page_insert_list_type;
5026 } else if (n == node_next(contribute_head)) {
5027 return contribute_list_type;
5028 } else if (n == node_next(page_head) || n == lmt_page_builder_state.page_tail) {
5029 if (istail && n == lmt_page_builder_state.page_tail) {
5030 *istail = 0;
5031 }
5032 return page_list_type;
5033 } else if (n == node_next(temp_head)) {
5034 return temp_list_type;
5035 } else if (n == node_next(hold_head)) {
5036 return hold_list_type;
5037 } else if (n == node_next(post_adjust_head) || n == lmt_packaging_state.post_adjust_tail) {
5038 if (istail && n == lmt_packaging_state.post_adjust_tail) {
5039 *istail = 0;
5040 }
5041 return post_adjust_list_type;
5042 } else if (n == node_next(pre_adjust_head) || n == lmt_packaging_state.pre_adjust_tail) {
5043 if (istail && n == lmt_packaging_state.pre_adjust_tail) {
5044 *istail = 0;
5045 }
5046 return pre_adjust_list_type;
5047 } else if (n == node_next(post_migrate_head) || n == lmt_packaging_state.post_migrate_tail) {
5048 if (istail && n == lmt_packaging_state.post_migrate_tail) {
5049 *istail = 0;
5050 }
5051 return post_migrate_list_type;
5052 } else if (n == node_next(pre_migrate_head) || n == lmt_packaging_state.pre_migrate_tail) {
5053 if (istail && n == lmt_packaging_state.pre_migrate_tail) {
5054 *istail = 0;
5055 }
5056 return pre_migrate_list_type;
5057 } else if (n == node_next(align_head)) {
5058 return align_list_type;
5059 } else if (n == lmt_packaging_state.page_discards_head) {
5060 return page_discards_list_type;
5061 } else if (n == lmt_packaging_state.split_discards_head) {
5062 return split_discards_list_type;
5063
5064
5065 } else {
5066 return -1;
5067 }
5068};
5069
5070void tex_set_special_node_list(special_node_list_types list, halfword head)
5071{
5072 switch (list) {
5073 case page_insert_list_type:
5074
5075 if (head) {
5076 node_next(page_insert_head) = head;
5077 node_next(tex_tail_of_node_list(head)) = page_insert_head;
5078 } else {
5079 node_next(page_insert_head) = page_insert_head;
5080 }
5081 break;
5082 case contribute_list_type:
5083 node_next(contribute_head) = head;
5084 contribute_tail = head ? tex_tail_of_node_list(head) : contribute_head;
5085 break;
5086 case page_list_type:
5087 node_next(page_head) = head;
5088 lmt_page_builder_state.page_tail = head ? tex_tail_of_node_list(head) : page_head;
5089 break;
5090 case temp_list_type:
5091 node_next(temp_head) = head;
5092 break;
5093 case hold_list_type:
5094 node_next(hold_head) = head;
5095 break;
5096 case post_adjust_list_type:
5097 node_next(post_adjust_head) = head;
5098 lmt_packaging_state.post_adjust_tail = head ? tex_tail_of_node_list(head) : post_adjust_head;
5099 break;
5100 case pre_adjust_list_type:
5101 node_next(pre_adjust_head) = head;
5102 lmt_packaging_state.pre_adjust_tail = head ? tex_tail_of_node_list(head) : pre_adjust_head;
5103 break;
5104 case post_migrate_list_type:
5105 node_next(post_migrate_head) = head;
5106 lmt_packaging_state.post_migrate_tail = head ? tex_tail_of_node_list(head) : post_migrate_head;
5107 break;
5108 case pre_migrate_list_type:
5109 node_next(pre_migrate_head) = head;
5110 lmt_packaging_state.pre_migrate_tail = head ? tex_tail_of_node_list(head) : pre_migrate_head;
5111 break;
5112 case align_list_type:
5113 node_next(align_head) = head;
5114 break;
5115 case page_discards_list_type:
5116 lmt_packaging_state.page_discards_head = head;
5117 break;
5118 case split_discards_list_type:
5119 lmt_packaging_state.split_discards_head = head;
5120 break;
5121 }
5122};
5123
5124scaled tex_effective_glue(halfword parent, halfword glue)
5125{
5126 if (parent && glue) {
5127 switch (node_type(glue)) {
5128 case glue_node:
5129 case glue_spec_node:
5130 switch (node_type(parent)) {
5131 case hlist_node:
5132 case vlist_node:
5133 {
5134 double w = (double) glue_amount(glue);
5135 switch (box_glue_sign(parent)) {
5136 case stretching_glue_sign:
5137 if (glue_stretch_order(glue) == box_glue_order(parent)) {
5138 w += glue_stretch(glue) * (double) box_glue_set(parent);
5139 }
5140 break;
5141 case shrinking_glue_sign:
5142 if (glue_shrink_order(glue) == box_glue_order(parent)) {
5143 w -= glue_shrink(glue) * (double) box_glue_set(parent);
5144 }
5145 break;
5146 }
5147 return (scaled) lmt_roundedfloat(w);
5148 }
5149 default:
5150 return glue_amount(glue);
5151 }
5152 break;
5153 }
5154 }
5155 return 0;
5156}
5157 |