From 9fbac07cfaf6f8c5db0aeeae66423e5fedff8adc Mon Sep 17 00:00:00 2001 From: Karl Berry Date: Mon, 8 Mar 2021 19:16:10 +0000 Subject: knuth tuneup2021 update from pwebmac/knuth-lib.tar.gz git-svn-id: svn://tug.org/texlive/trunk@58228 c570f23f-e606-0410-a88d-b1316a301751 --- .../texmf-dist/doc/generic/knuth/errata/mf84.bug | 2443 -------------------- 1 file changed, 2443 deletions(-) delete mode 100644 Master/texmf-dist/doc/generic/knuth/errata/mf84.bug (limited to 'Master/texmf-dist/doc/generic/knuth/errata/mf84.bug') diff --git a/Master/texmf-dist/doc/generic/knuth/errata/mf84.bug b/Master/texmf-dist/doc/generic/knuth/errata/mf84.bug deleted file mode 100644 index c6349b896da..00000000000 --- a/Master/texmf-dist/doc/generic/knuth/errata/mf84.bug +++ /dev/null @@ -1,2443 +0,0 @@ -This file has been updated periodically ever since METAFONT84 was born. -What you are about to read is "authentic source material" from the -early days before the program converged. Module numbers on the first -entries may bear little relation to those in Volume D. - -Entries are in chronological order; thus the most recent news appears -at the bottom of the file. - -------------------------------------------------------------------------------- - -(rough list of all bugs found in MF after it passed syntax check) -Starting with Version -100.0: [Mar 27, first run, about 00:30] -1. fix_date_and_time was badly patched in INIMF. -2. cur_tok function forgot "cur_tok:=p" at the end; PASCAL doesn't catch that. -3. "multiletter control sequences" msgs should say "symbolic tokens". -Version -99.0: [still Mar 27, done while waiting for WEAVE/TeX output] -4. do_statement should initialize cur_type:=vacuous. -5. find_variable has misplaced p:=equiv(p). -6. one-character primitives shouldn't decrease str_ptr. -7. clear_symbol had "q" at end where I meant to say "p". -8. help message for extra token flushing improved. -9. "buffer[k]" should be "buffer[j]" for 1-character id_lookup. -10. def_delims forgot to get_next afterwards. -11. type_command at beginning of statement wasn't diverted. -12. menu always came out after help message. -13. forgot to return after getting num/str token from token list. - Version -98.0: [March 28] -14. scan_declared_variable flushes too much. -15. ordered pairs: one level of indirection was forgotten. -16. type declarations must add "unknown" bit. -17. semicolon+ added to do_statement cases. -18. base_ident should get max_str_ref. -19. "internal[...]" missing in date for base_ident. -20. do_binary(p,c) should be do_binary(p,d) after continue_path -21. in scan_def after get_clear_symbol I need to get_next. -22. get_next needed at end of scan_def. -23. get_next needed at end of mode_command processing. -24. randomseed missing error typo: `;' for `:='. -25. print_nl("") at beginning of show. -26. refcounts on macro calls were incremented twice. -27. forgot to advance loc after getting num/str token from token list. -28. "/" has the wrong command code. -29. get_x_next needed after, e.g., "1/2" in scan_primary. -30. take_fraction should be make_fraction in call of frac_mult. -31. v:=dep_list(v) forgotten in dep+dep branch of add_or_subtract. -32. q:=link(q) etc misplaced and omitted in p_plus_fq and p_plus_q. -33. dep_finish recycled a dependency list twice. -34. call of dep_finish should use null not cur_exp. -35. decided that "3 3" shouldn't equal 9. -[also put in new code for the addto command] - Version -97.0: [March 29] -36. forget to set q:=qq in scan_expression. -37. first line of print_path: forgot print_ln. -38. typo in set_controls: right_y should be left_y. -39. toss_knot_list forgot that it has a circular list to toss. -40. print_exp shows big nodes backwards. -41. angle brackets didn't look good in print_exp; took them out. -42. left_brace must be between min_tertiary and max_tertiary. -43. prev_dep should point back to tail, not head, of previous list. - (that error was in encapsulate and ) -44. nonlinear_eq should leave node p vacant, sometimes. -45. conditional routine forgot that get_boolean starts with get_x_next. -46. forgot get_x_next in processing of else. -47. str_ref not initialized by make_string. -48. param_start not initialized properly. -49. "%EXPR" didn't look good in token list. -50. "{loop}" not necessary in forever loops; there's already enough. -51. macro name didn't come out right when tracing macros. -52. macro parameters weren't shown when tracing macros. -53. quote marks missing when displaying strings. -54. parameter names on macro call trace should look nicer. -55. statement beginning with bad token: error message needed. -56. `->' desired in context lines of macro. -57. forgot q:=loop_list_loc(s) in begin_iteration. -[also put in new code for shipout] - Version -96.0: [March 30] -58. forgot loop_type(s):=null in begin_iteration. -59. forgot value(p):=null after type(p):=type(pp) in find_variable. -60. forgot to delete_pen_ref after filling a contour. -61. check that it's a cycle before calling make_spec. -62. "if tracing_stats>0" should be "if internal[tracing_stats]>0"! -63. forgot get_next after showdependencies. -64. forgot link(r):=p at end of dependency list addition. -65. extra `get_x_next' in . -66. typos in last half of : mind the p's and q's. -67. take_fraction should be make_fraction in simple case of two givens. -68. in print_exp of unknown type, stop if v=null. -69. showtoken forgot to stop; also should be consistent with TeX. -70. "continue" label needed in error routine, after all. -71. id_lookup should treat length-one identifiers by simpler method. - (in particular, this allows it to find unprintable ones!) -72. need psi[n+1]:=psi[1] in cyclic case of make_choices. -73. tension/controls take primaries as arguments, not expressions. -74. print_spec didn't initialize octant. -75. print_spec: break lines into two, since they are quite long. -76. smooth_moves not called in fill_spec. -77. typo < for > in edge_prep. -78. edge tracing misses half the corners, and forgot to set trace_y. -79. edge_prep needs extra logic when rover=head. -80. make_good should compute cur_d based on good values, not original values; - but we sometimes need the other alternative too. -81. valid_sum: the test was backwards. -82. print_weight blunder: ho(q) should be ho(info(q)). -83. forgot init_gf in shipout. -84. typo in : if total_chars<>1 then print("s"). -85. initializations of ww, prev_w, and m were forgotten in ship_out. -86. typos in initialization of prev_m and gf_min_x. -87. forgot to update prev_n in ship_out. -88. relax becomes "expandable". -89. internal[x]>1 should be internal[x]>unity! -90. forgot to restore normal scanner_status in pass_text. -91. (end occurred when if...) was inevitable. -[also put in new code for openwindow, display] - Version -95.0: [April 1] -92. forgot to unscale the window numbers in that new code. -93. had w<0 test instead of w<=0 in . -94. prev_w:=w should be done in all cases of . -95. forgot get_x_next after scanning `1/2'. -96. in do_assignment, after recycle_value(p) I need to set type(p):=something. -97. omit `.' after the equivalent in showtoken. -98. in , I said "until q=p"; I meant "until q=value(p)". -99. print_macro_name said "info(link(a))"; meant "text(info(info(link(a))))". -100. forgot get_x_next after macro_call in scan_primary. -101. scan_primary installed dependent components badly (data structure error). -102. new_structure failed in case of generic_subscript (data structure error). -103. param_type case of print_cmd_mod had bad if/else nesting (language error). -104. null_path forgot to return a value (language error). -105. p_with_x_becoming_q had typos (q and f for x). -106. should end with cur_exp:=t, not r. -107. subscripted definitions: out of sync; scan_primary loop needs revision. -108. secondarydef went through scan_def instead of make_op_def. -109. make_op_def forgot the final get_next. -110. make_op_def also forgot to insert the general_macro preface. -111. showvar shows too much of macro variables. - Version -94.0: [April 4] -112. single_dependency needs to take account of the scale factor. -113. add_or_subtract starts out with wrong v value. [bug 31 was fixed wrong] -114. print_exp needs a case for t=independent. -115. also numeric_type, and case v=null of pair_type, transform_type. -116. end_token_list thought identity_macro and insertions had ref counts. -117. disp_var should display also in case of generic subscripts. -118. find_var should put value(pp):=null when it sets type(pp):=numeric_type. -119. yet another problem in : copy_dep_list(dep_list(q)). -120. scan_primary should flush_node_list(q) before make_exp_copy(p). -121. make_scaled arguments reversed in p_over_v. -[also added code for new internals: smoothing, autorounding] -[also added code for showstats] - Version -90.0: [April 5] -122. Should check range of variables when they become known. -123. should include begin...end (WEB language error). -124. forever should be followed by a colon. -125. dangling else problem in make_eq: "abc"="abc" considered false. -126. showstats, showtoken should read the semicolon before stopping. -127. print_variable_name balked at, e.g., xpart of a capsule. - Version -89.0: [April 6] -128. after &foo, shouldn't assume there's an input file present. -129. forever forgot get_next. -130. pair=path and path=pair should coerce the pair to be a path. -131. similarly in the operand to `addto'. -[added new code for cull command] -[minor revision of internal quantities; e.g., labeling is out, fontmaking is in] - Version -88.0: [April 7] -132. "string" operator is renamed "str". -133. min/max coordinates added to boc command. -134. labeling_command removed; it will be implemented in macros. -135. info(p) should be attr_loc(p) in flush_variable. -136. make_spec didn't realize the need for xh and yh. -137. gf_new_row parameters had sign reversed. -138. the "numeric" case was left out of recycle_value. -[added new code for special/numspecial] - Version -87.0: [April 13] -139. q:=qq should apply also after , in scan_expr. -140. param_size: better defined than a constant. -141. surprise: back_input fails when cur_cmd=expr_arg, as it changes limit. -142. forgot to change right_type(r). -143. show shows the whole path. -144. expr like 0..1 leads to with q undefined. -145. typos in , clobbered dx2 and used right_type(p) twice. -146. need to adjust expr_arg when macro is inside a macro! -147. expr_arg forbidden to be in a text argument. -148. frozen_relax added to prevent premature termination. -[I took out the code used for debugging the screen interface] -[added "cycle", a unary operator taking path to boolean] -[added the code for concatenation and for str and for xpart..yypart] - Version -86.0: [April 25] -149. not_scolded_yet was never set false after scolding. -150. Missing "q:=s" at the end of . -151. In @, add get_next after back_error. -152. New xpart routine didn't recycle other components of the big node. -[added the "hard_times" case of multiplication] -[added the complete set of boolean expressions] -[added the eight transformations, applied to three kinds of expressions] -[added the save command] -[added the interim command] -[added the let command] -[added the pen operations] -153. Incomplete help message on "Not a variable". -154. forgot begin...end in the last section of materialize_pen. -155. blunder : length(p,s,q) should be length(s,q,r). -156. : forgot begin...end here too. -157. "(newly created)" shd be " (newly created)". -158. path_trans: forgot to unstash the capsule p. -159. set_up_trans: transform_type should be transformed_by, in one place. -160. : had p instead of q, in several places. -161. edges_trans: an edges variable isn't in a capsule. - Version -85.0: [May 2] -162. begingroup ... endgroup should be allowed as compound statement. -163. pausing shouldn't clobber "showit". (WAITS version only) -164. Improved help message for isolated expressions. -165. Bad error recovery after "Not a variable" in showvar. -166. Typo in clear_symbol: name_type(p) instead of name_type(q). -167. "%" and ";" to be left out of file names being input. -168. dep_finish used v for two purposes; wrong declared type. -169. autorounding 2 suppresses correction when the derivative isn't critical. -170. tab characters should be changed to spaces on input. (WAITS version) -171. harmful goto: Forgot to |return| after path_trans and edge_trans. -[added ord, hex, oct, length, char, decimal, and jobname] - Version -80.0: [May 4] -172. showvar still screwed up. -173. don't clobber screen for prompt_input (WAITS only). -174. length of non-cyclic path is one too high. -175. evoked the wrong message. -176. better error message needed on `Equation cannot be performed'. -177. ">> " inserted before expression displays. -178. should dup_offset also when n=0. -179. pencircle was a factor of 2 too big. -180. cosine of 180 should be -1 exactly. -181. ord "" should be -1. -182. shipout should allow expressions as well as variables. -183. "mod outer_tag" needed in various tests on eq_type. -184. merge_edges forgot to adjust for changes in m_offsets. -185. typo, ww for w in print_pen. -186. typo, "outer" for "errhelp" in print_cmd_mod (message case). -[added "also"] -[added "message", "errmessage", "errhelp"] -[added "outer", "inner"] -[added "readterminal", "readstring"] - Version -79.0: [May 6] -187. read_toks forgot to include the general_macro token. -188. offset_prep should treat n=0 like n=1. -189. cusp transitions (from change 169) must be suppressed in envelope case. -190. shouldn't change xp or yp. -191. was used too late. -192. had a redundant test (a relic of old code). -193. wastefully made the same fraction three times. -194. doublepath should split the cycle. -195. `if k=0' in fin_offset_prep should have been `if k=1'. -196. `done:' misplaced in . -197. also move[move_ptr] should be initialized to 1 there, not 0. -198. skew is used with p=q in fill_envelope. -199. it's no use tracing subdivision for offsets, since everything is skewed. -200. in , round_unscaled should be floor_unscaled. -201. unskewing: wrong formula (x was .5 too large). -202. elliptical pens: better correction for the case gamma<=abs(alpha). -203. dual env_move was updated badly, in both and . -204. dual env_move to move: subscripts were off by 1. -205. should set ww:=knil(link(h)), not link(h). -[added ++] - Version -70.0: [May 9] -206. suppressed cusp rounding in envelope case too. -207. `show' should use `>> ' when it shows an expression. -208. streamlined the test for bad lambda and mu in |skew|. -209. after linear_eq, must check if type(cur_exp)=known. -210. print_spec surprise: contours might never travel toward the first octant! -211. t0,t1,t2 sign was reversed in . - Version -69.0: [May 10] -212. "showvar" changed to "showvariable". -213. typo: r for r_delim in . -214. "newinternal" feature added. -215. needs to update envmove at end of loop. -216. smooth_moves shouldn't affect the extreme points. -217. floor(unity*(n-1)/n) is unity when n is large; need to be more careful. -218. major improvements to rounding, based on new theory of (x+eps,y+eps^2). -219. pen offsets made symmetrical about the origin. -220. p:=half(p+q) overflow problem in take_fraction, take_scaled. -221. cull_edges now updates the max/min values too. -222. make_spec needs to be more bullet-proof to rounding errors; added `dest's. -223. xmult/ymult/zmult changed to xscaled/yscaled/zscaled. -224. elliptical pens improved by temporarily allowing zero-length lines. -[added edge transposition algorithm] - Version -67.0: [May 17] -225. copy can encounter a vacuous expression, e.g. in a parameter. -226. xy_swap_edges mustn't change w when inserting a large weight. -227. in #222, had typo pp for r in . -228. in #222, incorrectly assumed local max = global max of cubic. - Version -66.0: [May 19] -229. bad_binary(c,p) should have been bad_binary(p,c). -230. enabled comparison of unknown strings. -231. fixed ring_delete to avoid unexpected scolding. -232. should store character width info even when proofing<0. -[added all the TFM commands and output routines] -[added the `substring' operation] -[added `point', `precontrol', `postcontrol'; deleted `direction'] - Version -65.0: [May 24] -233. Change error message `(t)point(u)' to `point(t)of(u)'. -234. newinternal to allow a list of tokens. -235. In , should check for overflow before begin_token_list. -236. scan_def didn't allow for the case warning_info=null. - Version -60.0: [May 25] -237. increased param_size. -238. added . -239. stopped too early if the first cubic was dead. -240. bad_unary, bad_binary should distinguish pair from unknown pair. -241. yet another "m was scaled instead of fraction. - Version -59.0: [May 27] -245. break up initialize routine into two parts (cf init_prim in TeX) - Version -58.0: [May 28] -246. do_ship_out should scan_expression, not scan_primary. -247. offset_prep might clobber node q, so we need to search for q again. -248. pair "1" = true! (blunder in type_test) -249. allow strings x in `def f(expr x)=def g=x enddef enddef'. -250. allow exprs in text parameters, in sufficiently easy cases. -251. check right delimiters in macro_call. -252. "Bad window number" message gave unscaled value. -253. turnaround feature improves automatic rounding slightly. -254. primaries changed to expressions in window and cull commands. -255. scan_expression should make (0,0){0,0} a path, not a future path. -256. showvariable and showtoken to allow lists; all shows made consistent. -257. new internal quantity "windingcheck". -258. delete warning message about edges never used. -259. vardef: group the righthand side. -260. show commands stop once each. -261. cur_type should be vacuous after equation or assignment on outer level. - Version -57.0: [June 4] -262. added xyzzy diagnostic about effect of autorounding. -263. make_moves now puts xi_corr,eta_corr into halving. -[otherwise "draw (0,0)..(9,-.00002)" and "draw (0,-.00002)..(9,0)" fail badly!] - Version -56.0: [June 6] -264. smooth_moves changed completely; now is LR symmetric, cleaner. -265. changed "unknown" to "known". -266. pair to path conversion now done on length, makepen, reverse, etc. -267. cycle now defined on arguments of any type. -268. (re 218) sign was flipped in ceiling correction of . -[added union, subpath, penoffset, directiontime, intersectiontimes] - -Note: the first two draw statements in PENS.mf show an interesting effect. -With autorounding, the curves are noticeably better, esp the small one. -But there are two "holes", because of tiny discrepancies that I believe -are unavoidable. -Added later: Actually these are avoided by the new smooth_moves, but -certain others will not be. - Version -50.0 [June 30] -269. smoothing to be shut off at the retrograde transitions -270. more care needed in the rootfinding part of find_direction_time. -271. improved error recovery after "Isolated expression". - Version -40.0 [July 3] --- the first version to be "complete"! -272. trivial change in . -273. check that halfwords are large enough to hold edge/weight data. -274. `path reverse (0,1)' should be true. -275. xy_swap_edges might empty the structure; then x_reflect will fail! -276. fix_offset was being done too often, due to improper range test. -277. parameters come out even when tracingonline=0. -278. step-until wasted r and didn't check syntax carefully. -279. had typo: `line' for `group_line'. -280. "You can't dump in a group" error was impossible. -281. need better ETC cutoff in showmacro. -282. print_exp needs to handle independents, because it's used by disp_var. -283. suppress `#### xpart %CAPSULEnnnn' printouts. -[added code for everyjob; this version wasn't complete after all!] - Version -30.0 [July 9] -284. need better error/help after ` if s1=s2' when the strings are unknown. -285. removed autorounding>2; it was leading to more glitches than it was worth. -286. envelope filling of a cycle to be done by two calls of fill_envelope. -287. "null" changed to "vacuous". -288. cyclic path inserted in another path should retain its last arc. -289. introduce several dozen "put_get" errors for improved recovery. -290. suppress "with autorounding" when autorounding hasn't been set. -291. {loop value} came out even when tracingonline=0. -292. show commands should wake up the terminal before showing their output. -293. forgot error message in `if true else'. - Version -20.0 [July 14] -294. need to catch pens that are too large. -295. make_eq dassn't change lhs (because this clobbers the memory links later). -296. string usage is reported too high by showstats. -297. bilin1 and add_mult_dep can call p_plus_fq with type(q)=proto_dependent. -298. forgot to recycle pp. -299. in change number 286, the weight of the two paths should be the same. -300. print_ln sometimes changed to print_nl("") in order to avoid blank lines. -301. xyzzy to be combined with tracingedges. -302. good3 entries should be 1 and 2 (not 1 and 0), to give desired symmetry. - Version -10.0 [July 17] -303. had to add `new_if_limit' to `conditional'. -304. `else' can be incomplete as well as `if' and `elseif'. -305. new help "You can't redefine a parameter." -306. print_edges should use cur_edges, because print_weight does. -307. cull shouldn't round; it should use ordinary inequalities. -308. obliterated variable left `0' token hanging in scan_primary. -309. forgot recycle_value(p) in . -310. forgot to check improper culling amounts. -311. `on' to be changed to `inwindow'. -312. >=max_tfm_dimen should be simply >. - Version -9.0 [July 19] -313. max_tfm_dimen needs to be decreased by design_size div 2^21. -314. merge test data reporting into the screen display routines. -315. use @# in printout at time of macro expansion tracing. -316. bad recovery after "Incomplete string" error. -317. @ should be usable as a parameter. -318. spacing bad on `missing of' and `too many parameters' errors messages. -319. keep track of largest str_ptr and pool_ptr values; showstats on two lines. - Version -8.0 [July 26] [introduced new test routines to study memory usage] -320. make_pen doesn't recycle the knots -321. flush_below often says free_node(2) on node of size 3. -322. make_eq should recycle and free; do_equation shouldn't -323. re #298 and #309: should also free the value nodes! -324. the replacement text of a bad_var definition should be recycled. -325. token lists left unrecycled in error recovery of addto, cull, display. - Version -7.0 [July 27] -326. showall to put "(see the transcript file)" after >> if not tracingonline. -327. remove redundant code: hex in print_the_digs; second l=1 in idlookup. -328. procedures never called: b_open_in; round_scaled. -329. need to zero cur_mod after back_expr in . -330. now catches also numbers that round to 1.0. -331. known_pair logic was obsolete; now it is massively simpler. -332. fix_check_sum now zeroes the negative bytes; this simplifies other code. -333. show_dependencies not to show parts of capsules. -334. forgot to set fix_needed:=false! -335. move fix_needed from add_or_subtract to dep_finish. -336. test fix_needed in bilin1 and add_mult_dep. -337. after back_expr in , forgot to unstash p. - Version 0.0 [July 28] [Hurray! The preliminary TRAP test is fully passed.] -338. corrected blunder in definition of trans_spec type. (found by Karney) -339. less extreme starting values of gf_min_x and its cousins. -340. uninitialized left_curl was possible. (found by John Hobby) -341. In , need to test sign before the `div 3' ops. -342. In pyth_add, remove `+2' when dividing by 4, to prevent overflow. -343. "Not a variable" changed to "Not a suitable variable". -344. known_pair forgot to reset cur_type. -345. round and floor procedures need to work in the presence of huge arguments. -346. major revision to allow independent variables to disappear silently: -346a. delete null_path and . -346b. delete the hard part of ring_delete, and delete . -346c. stash/unstash/flush_cur_exp routines to allow independent type. -346d. print_exp to allow a ring that contains only capsules. -346e. becomes (major new code). -346f. stash_in needs code to handle the case cur_type=independent. -346g. negation needs code to handle the case cur_type=independent. -346h. take_part needs code to handle the case cur_type=independent. -346i. do_binary needs code to handle either or both operands independent. -346j. frac_mult needs code to handle the case cur_type=independent. -346k. make_eq and try_eq too. -346l. linear_eq needs to check if cur_exp=x and cur_type=independent. -346m. linear_eq displays new dependency only when lhs is interesting. -347. minor improvement for coding style/brevity: the "interesting" function. -348. test `if t, didn't watch for coefficients zeroed. -352. check_mem now checks also the links in the dependency lists. -353. null_pen initialization belongs in , not . -354. fix_dependencies has to worry about coefficients dropping to zero. -355. add tracing to frac_mult. -356. need cur_sym>0 at the time of end_read_terminal. (found by S Robinson) - Version 0.1 [August 30] -357. Don't complain about winding_number<=0 when doing a doublepath. -358. Need to test for max_coef=0 in offset_prep. -359. Cusp detection should allow for more rounding error. -360. Major change to path syntax, allowing {dir}..{dir} path joins. -360a. `Fragments' disappear; new_fragment becomes new_knot. -360b. print_path has simpler conventions. -360c. future_path type disappears. -360d. left_brace renumbered and removed from scan_tertiary. -360e. some scan_tertiary code moves to new subroutine scan_direction. -360f. scan_expression has a bunch of new code. -361. scan_expression shouldn't have returned after cycle_hit. -362. abort_path, scrap_knot logic removed from scan_expression. - Version 0.2 [September 12] -363. new operator: makepath . -364. define point/precontrol/postcontrol at endpoints and beyond. (JDH) -365. union replaced by +; negation and subtraction allowed on edges. -366. another new operator: totalweight . (JDH's idea) -367. undelimited parameters may be preceded by an optional = or :=. -368. base_area_length was wrong. (affects CH files)(found by Pavel) -369. internal names to be allowable in suffixes. -370. label not_found was misplaced in do_add_to. (found by PasMESA translator) -371. progress report should be given at time of shipout. -372. procedures make_choices, make_spec,fill_envelope split into shorter pieces. -373. locals of cubic_intersection made global so that people could split it. - Version 0.3 [September 27] -374. allow ::= -375. equation that's off by .0001 shouldn't be called inconsistent. -376. bug in skew: must compute x_coord(q) and y_coord(q) exactly. -377. right/left/up/down to be assigned to octants 1/5/2/6; was 1/4/2/7. -378. boundedness to be allowed with any tension, and one-sidedly. -379. eliminate coordinate nodes in path lists by passing angles instead (JDH). -380. known_pair to free cur_exp after error msgs that might showdependencies. -381. scan_primary sometimes accessed num before it had a value (found by Pavel). -382. invalid characters should cause error message (suggested by PMB). - Version 0.4 [October 12] -383. allow `0' in response to error prompts. -384. put loop value on error context lines. -385. change `ord' to `ASCII'. -386. scantokens to be permitted; readterminal goes away. -387. expandafter to be permitted. -388. improved overflow conventions on make_fraction, make_scaled. -389. variable= should get its own error message. -390. nice_pair first argument can be any integer. -391. new feature, shortshow commands that don't pause. -392. "harmless" bug in negate_edges, the sorted list can get out of sorts. -393. ni too skimpy (15 instead of 63). (JDH) -394. loop_ptr not initialized. (found by Paul Richards) -395. bug in , q=null should goto done1. (Richards) -396. empty_edges macro added for readability. -397. x_reflect_edges might as well fix the offset as it goes. -398. blunder: frozen_bad_vardef had the wrong eq_type. -399. "name" changed to "tag". -400. check_arith inserted after division of numeric tokens. -401. stop_bit was not initialized in . -402. char 127 to be a string of length 1; slow_print added (therefore). -403. pyth_sub added to the repertoire. -404. minor change to calls on "confusion" in make_fraction, make_scaled. (JJW) - Version 0.5 [November 9] -405. 4095.999999 should be erroneous. -406. length to give the absolute value; argd changed to "angle". -407. get_next changed to get_x_next wherever possible. -408. z1..z2{curl 0} should be equivalent to z1..{curl 0}z2. -409. scantokens "" should be fast. -410. allow undelimited suffix and text parameters. -411. warningcheck to allow large variable values passed over silently. -412. "edges" changed to "picture". -413. "winding" changed to "turning". -414. had typo, "p" for "q". -415. elliptical pens should have axis symmetry. -416. slow_add introduced to catch arithmetic overflow on addition. -417. add a turningnumber primitive. -418. no carriage return between ">>" and "Edge structure...". -419. install new memory management routines (from TeX version 1.3). -420. generalized cull command. (suggested by Bruce Leban) -421. bad goto: `x..' reports that x is vacuous, loses value of x. -422. shortshows replaced by an internal variable "showstopping". -423. major change, capsule tokens: lots of code and restrictions gone! (JDH) -424. substring(a,b), subpath(a,b) to reverse the result when a>b. -425. new GF format: z goes away. (suggested by ALS) -426. another GF mod: chardw replaced by chardx/chardy, which are scaled. (PMB) -427. make `&' have the same precedence always (not different for strings). -428. wrong error message for 2"s" (bug introduced in change 369). -429. variable l in show_context has to be declared type integer. -430. bug in chop_path when both limits are large. - Version 0.6 [December 10] -431. xoffset and yoffset to be added by shipout. [this affects GF comments] -432. wake_up_terminal, not t_open_out, before "Ouch..." (Scott Robinson) -433. undelimited suffix parameters to allow an optional delimiter, disallow =. -434. showall... to be eliminated; tracingcapsules added. -435. allow undelimited parameters after delimited ones. -436. nullpen test in addto should test for any one-point pen. -437. granularity parameter to affect autorounding (Bruce Leban) -[this leads to major improvements suggested by JDH; lots of code changes!] -[basically, make_spec is now responsible for autorounding; fill_spec just fills] -438. node_size overflow problem must be prevented. (Paul Richards) -439. allow unary + with a picture. -440. nullpen should transform quickly to itself, if not shifted. -441. print_edges should skip over null rows, if it doesn't already. -442. open_base_file improved (following TeX's change number 302). -443. output initialization improved (following TeX's change number 303). -444. operators shouldn't fail because future pen isn't a pen. (JDH) -445. intersection routine to quit in hard cases. (DRF) -446. angle routine was off by epsilon on negative arguments. (Karney) -447. octant assignment should look ahead further in ambiguous cases. (JDH) -448. forgot that right_type(r)=endpoint could happen. -449. turning_number calculated directly, not times 8. -450. floor_scaled made more efficient by trading subtraction for multiplication. -451. doublepath autorounding to compromise between east and west. (JDH) -452. codes of picture_type and path_type interchanged, to simplify a "case". - Version 0.7 [January 17, 1985] -453. def to allow both := and =. (NB) -454. "keeping" and "dropping" instead of "including" and "excluding". (HWT) -455. (see the transcript...): why, when tracingonline>0? -456. dead cubics need to be removed also before xy_round. (NB) -457. [re 433] I said get_x_next twice; a blunder. - Version 0.75 [January 23, 1985] -458. Abbreviated boc command makes GF format more attractive for lowres. (GusF) - Version 0.76 [February 2] -459. known and unknown might as well both be primitive. -460. ab_vs_cd(a-d,b,c-b,d) simplifies to ab_vs_cd(a,b,c,d). (JDH) -461. (from change 435) must use k, not n. -462. (from change 458) max_new_row added, since 165 wasn't updated to 164. - Version 0.77 [February 16] -463. abbreviated version of tracingspecs is desired for turning number errors. -464. improved octant number in pathological cases of quadrant_subdivide (JDH) -465. xoffset,yoffset communicated to GF file when proofing>0. -466. Poirot changed to Marple. -467. reverse starts the reversed path at the wrong time. -468. Extra help given after `undefined coordinate' errors. -469. Keep segment numbers from overflowing max_halfword. (JDH) -470. Ditto for pen offset slope numbers. -471. n_magic had min_halfword with wrong sign. (John Johnson) - Version 0.80 [April 1] -472. In errhelp, % means , %% means %. (BPL) -473. tracing of envelopes should give symbolic octant names. -474. (-x mod y) should be ((-x) mod y) in good_val. -475. crossingpoint could overflow on 32-bit machines. (BPL) -476. Improvements to abbreviated format of number 463. - Version 0.81 [April 4] -477. `I hide(showdependencies)' in hint to become `I ???'. -478. print_strange shouldn't wake up the terminal in scroll mode. (cf 463) -479. flush_list procedure made a bit faster. (DRF) -480. bounded velocities to be multiplied by .999 for safety. -481. Detect error in declaration that tries to extend a vardef. -482. print_strange puts turns in parentheses (cf 463). -483. make_name_string shouldn't ever cause string space overflow. -484. allow xscaled m yscaled n. -485. checksum should consider values relative to designsize. (DRF) -[I also increased max_strings to 2000.] - -[Note: Neenie found a case where missing pixels can occur, due to -inconsistent rounding between left-to-right and right-to-left subdivision: -pickup pencircle; draw -(0,126)..controls (130.29451,126) and (288,126.00002) - ..(288,36)..controls (288,143.99998) and (132.97438,144) - ..(0,144)..controls (0,138) and (0,132) - ..cycle; -The "right" way to fix this would be to develop a make_spec routine for -non-cycles, and to copy a reversed spec, so that double paths would be -guaranteed self-inverse. However, my later experiments showed that -autorounding wasn't nearly as useful as I had expected it to be, hence I -decided not to waste time beefing up this routine; no satisfactory -automatic approach to rounding occurs to me.] - Version 0.90 [May 10] -486. 180-degree turns to be clockwise for half of doublepath cycles. -487. introduce fillin parameter. -488. `numeric_type' moved before `known', so that print_exp works (Richards). -489. numeric_type as unary op should include independent in its range (cf 346). - Version 0.91 [May 13] -490. show_token_list gets null_tally parameter. -491. if bad>0, change the code as in TeX changes 315, 316. -492. batchmode change as in TeX 317. -493. "and double autorounding" to be traced, if appropriate. -494. introduce tracingrestores. - *`restoring a bad variable'? -495. put decimal number into gf extension -496. mediation put into scan_primary, so that round .5[a,b] works properly. -497. cubic_intersection now has |tol| to compensate for rounding errors. -498. find_direction_time needs to worry about degenerate case x3=y3=0. -499. crossing_point(a,b,0) now yields fraction_one if a,b>0. -500. diag_round shouldn't insist that b-a is even (see below). -501. macro_call will show_macro with much larger limit. -502. TFM file statistics are logged too. - -* Here's an example (found by Neenie) explaining bugfix 500: -autorounding:=2; draw -(7.03159,-9.31831)..controls (12.14732,-9.4386) and (17.4299,-6.82948) - ..(21.60132,0)..controls (27.47417,9.61507) and (37.87402,15.58647) - ..(43.74687,25.20154)..controls (51.16223,37.34201) and (57.31,50.171) - ..(63.45776,63.00002) withpen pencircle; -The missing pixels are due to the following curious circumstances: (1) the -middle cubic splits into three, when subdividing into octants; (2) the reverse -curve splits too but with slightly different rounding, off by 1; (3) the old -diag_round routine, when it ensures that b-a is even, computes aa=a+1 on -one side of the curve, but aa=a-1 on the other side, thus making the -rounding "safe" on only one side. (Namely, on one side we have consecutive -values - b=1317666 a=1310720 - b=1329617 a=1310721 -and on the other side, - b=-1329618 a=-1310720 - b=-1317667 a=-1310721.) - -* Here's an example (by JDH) showing the necessary of bugfix 497: -path p[]; -p1 = (1,0)..controls (1,0.10493) and (0.98347,0.20921) - ..(0.95105,0.30902)..controls (0.91862,0.40881) and (0.8707,0.50288) - ..(0.80902,0.58778); -p2 = (0,0)..controls (0.63403,0.20601) and (1.26807,0.41203) - ..(1.9021,0.61804); -show p1 intersectiontimes p2; % (-1,-1), without `tol' -pickup pencircle; -currenttransform := identity scaled 150; -draw p1; draw p2; -showit; % but they clearly intersect - Version 0.95 [Aug 12] -503. `Se' changed to `SSE', etc. (suggested by RFS) -504. Inconsisting diagonal rounding was introduced in bugfix 500. - -[the following lines from @ in diag_round: - if aa>bb then cc:=dd-half(aa-bb-1)@+else cc:=dd-half(aa-bb+1) - if a>b then c:=d-half(a-b-1)@+else c:=d-half(a-b+1) -were replaced respectively by: - if right_type(p)>switch_x_and_y then cc:=dd-half(aa-bb+1) - else cc:=dd-half(aa-bb-1) - if right_type(p)>switch_x_and_y then c:=d-half(a-b-1) - else c:=d-half(a-b+1) -in order to make the rounding consistent on adjacent octants; -the following command caused `this can't happen': -fill (33,7)..controls (32.63094,5.70827) and (32.06163,3.716) - ..(31.59488,3.36667)..controls (31.10509,3.00009) and (29.14824,3) - ..(27.85318,3)..controls (27.85286,3) and (23.84952,3) - ..(23.8492,3)..controls (23.73282,2) and (23.61646,1) - ..(23.50008,0)..controls (26.66672,0) and (29.83336,0) - ..(33,0)..controls (33.66667,2.33333) and (34.33333,4.66667) - ..(35,7)..controls (34.33333,7) and (33.66667,7) - ..cycle;] - Version 0.96 [Aug 17] -505. allow comparison of transforms. [test by trying t=t when t is new...] -506. {restoring...} shouldn't get through when tracingonline=0. -507. better error message needed on `interim alpha:=0', `interim 0:=0'. -508. make_op_def should put parameters in the other order. -509. should say get_x_next, not get_next. -510. unif_rand to allow negative x, save on error messages. -511. tidy up chop_string when b<0 and/or a>l. -512. randomseed is automatically logged. -513. change 495 messed up if gf file couldn't be opened. (found by DRF) -[In INIMF.CH, 3-character extensions now have 0--9 or A--Z as leading digit.] - Version 0.97 [Sep 5] -514. a[b,c] to be tried only if a is numeric type. -515. simplified the code for length_op(string_type). -516. citations of `Chapter xx' now replaced by correct references. -517. to be in stat...tats version only. -518. remove extra space after and . -519. offsets should be included in the tracingoutput output. -520. a vacuous expression should be considered known. -521. charlist syntax changed from commas to colons. -[also the WAITS version command-line reader was fixed to handle `^^W'] - Version 0.99 [Sep 24] -522. vardef's begingroup...endgroup should be accessible. -523. allow an empty expression in for loops. - Version 0.999 [Oct 1] -524. "charfam" changed to "charext". -525. variable tt makes get_node slightly faster. (PROFILE suggests this) -526. cur_cmd<=max should be tested before cur_cmd>=min. (PROFILE) -527. fast_get_avail used in cur_tok and scan_primary. (PROFILE) - Version 0.9999 [Oct 27] -528. Major change to representation of independent variables - ("serial number" added so that MF's equation solving doesn't depend - on vagaries of storage allocation) - [module number change: new module between old 585 and 586] - [in terms of new numbering, modules 232, 585--587, 589, 594, 597, - 601, 608, 610, 816--817, 855, 1198--1199 were affected] -[I also reordered some of the cases in print_op, module 189, -so that the program could be condensed in published version] - Version 0.99999 [Nov 13] -529. forgot to decrease three_l in change 497! -530. cubic_intersection to give approximation if max_patience exceeded. -[the following example, found by NB, motivated this change: - show ( - (36.00104,26.99951)..controls (36.00131,26.99979) and (36.00146,27.00017) - ..(36.00146,27.00055) - )intersectiontimes( - (36,27.00055)..controls (45.17148,21.12364) and (55.83588,18) - ..(66.72873,18) - );] - Version 0.999999 [Dec 2] -531. hold_head needed (scan_toks calls cur_tok calls copy_edges). (D. Kosower) - Version 1.0 [January 4, 1986] -532. Optimization in module 1174, suggested by LER (3 Feb 86) -@x - if delta=0 then gf_out(skip0) - else begin gf_out(skip1); gf_out(delta); - end -@y - begin gf_out(skip1); gf_out(delta); - end -@z -*** Late copies of version 1.0 include this correction; -in particular, the program listing in Volume D was updated (with scissors)! - Changes subsequent to `Version 1.0' as published in C&T, Volume D: -533. Inconsistent punctuation in user messages (found by Karl Berry, June 86) -@x module 1134 -print_nl("Font metrics written on "); print(metric_file_name); -@y -print_nl("Font metrics written on "); print(metric_file_name); print_char("."); -@z (that was installed in version 1.1) - -534. Possible arithmetic overflows (found by Klaus Guntermann, July 86) -@x module 496 -while max_coef; -@y - internal[fontmaking]:=0; {avoid loop in case of fatal error} - @; -@z (that too was installed in version 1.2) - -536. Double rounding error should be avoided in make_ellipse (JDH, 22 Nov 86) -@x module 533 -d:=take_fraction(d,delta); -alpha:=abs(u); beta:=abs(v); -if alpha0 then d:=d-take_fraction(internal[fillin],beta+beta); -d:=(d+4) div 8; alpha:=alpha div half_unit; -@y -alpha:=abs(u); beta:=abs(v); -if alpha0 then - d:=d-take_fraction(internal[fillin],make_fraction(beta+beta,delta)); -d:=take_fraction((d+4) div 8,delta); alpha:=alpha div half_unit; -@z (That was the reason for version 1.3) - -537. Trivial change to a help message (version number is still 1.3). -@x module 1086 - ("Pretend that you're Miss Marple, examine all clues,")@/ -@y - ("Pretend that you're Miss Marple: Examine all clues,")@/ -@z - -538. Storage allocation can be more elegant and efficient (4/21/87) -@x module 169 -if r=p then if ((rlink(p)<>rover) or (llink(p)<>rover)) then -@y -if r=p then if rlink(p)<>p then -@z - -539. Unused variables can be eliminated. (Found by John Sauter, 5/5/87) -@x module 158 -@= -@!temp_ptr:pointer; {a pointer variable for occasional emergency use} - -@y (I used it only in my change file!) -@z -@x module 280 -@!r,@!s,@!t:pointer; {registers for list traversal} -@y -@!s,@!t:pointer; {registers for list traversal} -@z -@x module 284 -@!sine,@!cosine:fraction; {trig functions of various angles} -@y (the declarations in module 281 are correct, but in 284 they're superfluous) -@z -@x module 497 -var @!q,@!ww:pointer; {for list manipulation} -@!du,@!dv:scaled; {for slope calculation} -@!t0,@!t1,@!t2:integer; {test coefficients} -@!t:fraction; {place where the derivative passes a critical slope} -@!s:fraction; {slope or reciprocal slope} -@!v:integer; {intermediate value for updating |x0..y2|} -begin loop - begin q:=link(p); right_type(p):=k; -@y -var @!ww:pointer; {for list manipulation} -@!du,@!dv:scaled; {for slope calculation} -@!t0,@!t1,@!t2:integer; {test coefficients} -@!t:fraction; {place where the derivative passes a critical slope} -@!s:fraction; {slope or reciprocal slope} -@!v:integer; {intermediate value for updating |x0..y2|} -begin loop - begin right_type(p):=k; -@z -@x module 652 -@!s:0..param_size; {value of |param_start| on the current level} -@y who knows why that line was there? -@z -@x module 862 -var @!p,@!q,@!r:pointer; {for list manipulation} -@y -var @!p:pointer; {for list manipulation} -@z -@x module 985 -@!vv:scaled; {initial value of |v|} -@!q:pointer; {successor of |p|} -begin vv:=v; p:=cur_exp;@/ -@y -@!q:pointer; {successor of |p|} -begin p:=cur_exp;@/ -@z -@x module 1059 -@!t:small_number; {variant of |with_option|} -@y -@z - -540. Typo suppresses an error detection (Chris Thompson, 2May88) -@x module 963 - if txy mod unity=0 then if tyy mod unity=0 then -@y - if txx mod unity=0 then if tyy mod unity=0 then -@z - -541. get_x_token can lose a scanned declared variable (Chris Thompson, 4May88) -@x module 1011 -if equiv(x)=null then new_root(x); -@y -@z -@x module 1011 -done:scan_declared_variable:=h; -@y -done: if eq_type(x)<>tag_token then clear_symbol(x,false); -if equiv(x)=null then new_root(x); -scan_declared_variable:=h; -@z - -542. Avoid negative divisor rounding upward (Chris Thompson, fixed 19Jun88) -@x module 168 -else t:=(lo_mem_max+hi_mem_min+2) div 2; {|lo_mem_max+2<=t=1998 then t:=lo_mem_max+1000 -@z - -544. Avoid fatal_error after terminal eof (Tim Morgan, reported 25Oct88) -@x module 66 [serious problem occurred if this was called in open_log_file] -if not input_ln(term_in,true) then fatal_error("End of file on the terminal!"); -@y -if not input_ln(term_in,true) then t_open_in; -@z - -545. Force terminal output when open_log_file aborts (6Nov88) -@x module 789 - begin print_err("I can't write on file `"); -@y - begin selector:=term_only; print_err("I can't write on file `"); -@z - -546. By popular request, undo #544 and fix the bug a more complex way. -@x module 66 [this undoes change #544] -if not input_ln(term_in,true) then t_open_in; -@y -if not input_ln(term_in,true) then fatal_error("End of file on the terminal!"); -@z -@x module 87 [now we get to the new stuff] -begin if job_name>0 then selector:=term_and_log -@y -begin if log_opened then selector:=term_and_log -@z -@x module 88 - error; -@y - if log_opened then error; -@z -@x module 782 -@!job_name:str_number; {principal file name} -@y -@!job_name:str_number; {principal file name} -@!log_opened:boolean; {has the transcript file been opened?} -@z -@x module 783 -@=job_name:=0; -@y -@=job_name:=0; log_opened:=false; -@z -@x module 788 -selector:=log_only; -@y -selector:=log_only; log_opened:=true; -@z -@x module 789 -begin if interaction - print_file_name(cur_name,cur_area,cur_ext); print("'.");@/ - job_name:=0; history:=fatal_error_stop; jump_out; - end; {abort the program without a log file} -@y -begin selector:=term_only; -@z -@x module 1023 [this change is optional, but it's a slight improvement] - if job_name<>0 then selector:=selector+2; -@y - if log_opened then selector:=selector+2; -@z -@x module 1205 -if job_name>0 then -@y -if log_opened then -@z -@x module 1208 -if job_name>0 then {the log file is open} -@y -if log_opened then -@z - -547. String startup problems corresponding to TeX change 355 (17 Jul 89) -@x module 30 (Warning: This affects most change files!) - overflow("buffer size",buf_size); -@:METAFONT capacity exceeded buffer size}{\quad buffer size@> -@y - @; -@z -@x module 34 -consist of the remainder of the command line, after the part that invoked \MF. -@y -consist of the remainder of the command line, after the part that invoked \MF. - -The first line is special also because it may be read before \MF\ has -input a base file. In such cases, normal error messages cannot yet -be given. The following code uses concepts that will be explained later. - -@= -if base_ident=0 then - begin write_ln(term_out,'Buffer size exceeded!'); goto final_end; -@.Buffer size exceeded@> - end -else begin cur_input.loc_field:=first; cur_input.limit_field:=last-1; - overflow("buffer size",buf_size); -@:METAFONT capacity exceeded buffer size}{\quad buffer size@> - end -@z -@x module 1193 -k:=pool_ptr-4; undump_four_ASCII -@y -k:=pool_ptr-4; undump_four_ASCII; -init_str_ptr:=str_ptr; init_pool_ptr:=pool_ptr;@/ -max_str_ptr:=str_ptr; max_pool_ptr:=pool_ptr -@z -@x module 1204 -tini@/ -@y -init_str_ptr:=str_ptr; init_pool_ptr:=pool_ptr;@/ -max_str_ptr:=str_ptr; max_pool_ptr:=pool_ptr; fix_date_and_time; -tini@/ -@z -@x module 1204 -init_str_ptr:=str_ptr; init_pool_ptr:=pool_ptr;@/ -max_str_ptr:=str_ptr; max_pool_ptr:=pool_ptr;@/ -@y -@z - -548. Major changes to allow 8-bit input, cf. TeX82 #359 (11 Sep 89). -@x module 18 -@!ASCII_code=0..127; {seven-bit numbers} -@y -@!ASCII_code=0..255; {eight-bit numbers} -@z -@x module 19 -@d last_text_char=127 {ordinal number of the largest element of |text_char|} - -@= -@!i:0..last_text_char; -@y -@d last_text_char=255 {ordinal number of the largest element of |text_char|} - -@= -@!i:integer; -@z -@x module 21 -xchr[0]:=' '; xchr[@'177]:=' '; - {ASCII codes 0 and |@'177| do not appear in text} -@y -@z -@x module 22 -for i:=1 to @'37 do xchr[i]:=' '; -@y changing ' ' to chr(i) here will allow all 8-bit characters to get in -for i:=0 to @'37 do xchr[i]:=' '; -for i:=@'177 to @'377 do xchr[i]:=' '; -@z -@x module 23 -for i:=1 to @'176 do xord[xchr[i]]:=i; -@y -for i:=@'200 to @'377 do xord[xchr[i]]:=i; -for i:=0 to @'176 do xord[xchr[i]]:=i; -@z -@x module 37 -@= -@!pool_pointer = 0..pool_size; {for variables that point into |str_pool|} -@!str_number = 0..max_strings; {for variables that point into |str_start|} - -@ @= -@!str_pool:packed array[pool_pointer] of ASCII_code; {the characters} -@y [OK to make si(#)==#-128 and so(#)==#+128 (without parens) in change files] -Some \PASCAL\ compilers won't pack integers into a single byte unless the -integers lie in the range |-128..127|. To accommodate such systems -we access the string pool only via macros that can easily be redefined. - -@d si(#) == # {convert from |ASCII_code| to |packed_ASCII_code|} -@d so(#) == # {convert from |packed_ASCII_code| to |ASCII_code|} - -@= -@!pool_pointer = 0..pool_size; {for variables that point into |str_pool|} -@!str_number = 0..max_strings; {for variables that point into |str_start|} -@!packed_ASCII_code = 0..255; {elements of |str_pool| array} - -@ @= -@!str_pool:packed array[pool_pointer] of packed_ASCII_code; {the characters} -@z -@x module 41 -begin str_pool[pool_ptr]:=#; incr(pool_ptr); -@y -begin str_pool[pool_ptr]:=si(#); incr(pool_ptr); -@z -@x module 45 - begin if str_pool[j]<>buffer[k] then -@y - begin if so(str_pool[j])<>buffer[k] then -@z -@x module 47 -var k,@!l:0..127; {small indices or counters} -@y -var k,@!l:0..255; {small indices or counters} -@z -@x module 47 -@; -@y -@; -@z -@x module 48 -@ @= -for k:=0 to 127 do - begin if (@) then - begin append_char("^"); append_char("^"); - if k<@'100 then append_char(k+@'100) - else append_char(k-@'100); -@y -@ @d app_lc_hex(#)==l:=#; - if l<10 then append_char(l+"0)@+else append_char(l-10+"a") - -@= -for k:=0 to 255 do - begin if (@) then - begin append_char("^"); append_char("^"); - if k<@'100 then append_char(k+@'100) - else if k<@'200 then append_char(k-@'100) - else begin app_lc_hex(k div 16); app_lc_hex(k mod 16); - end; -@z -@x module 59 - begin print_char(str_pool[j]); incr(j); -@y - begin print_char(so(str_pool[j])); incr(j); -@z -@x module 60 - begin print(str_pool[j]); incr(j); -@y - begin print(so(str_pool[j])); incr(j); -@z -@x module 85 - begin if str_pool[j]<>"%" then print(str_pool[j]) - else if j+1=str_start[err_help+1] then print_ln - else if str_pool[j+1]<>"%" then print_ln -@y - begin if str_pool[j]<>si("%") then print(so(str_pool[j])) - else if j+1=str_start[err_help+1] then print_ln - else if str_pool[j+1]<>si("%") then print_ln -@z -@x module 199 -char_class[127]:=invalid_class; -@y -for k:=127 to 255 do char_class[k]:=invalid_class; -@z -@x module 200 -@d hash_is_full == (hash_used=1) {test if all positions are occupied} -@d eq_type(#) == eqtb[#].lh {the current ``meaning'' of a symbolic token} -@d equiv(#) == eqtb[#].rh {parametric part of a token's meaning} -@d hash_base=129 {hashing actually starts here} -@y [incidentally I fixed a bug re hash overflow here] -@d eq_type(#) == eqtb[#].lh {the current ``meaning'' of a symbolic token} -@d equiv(#) == eqtb[#].rh {parametric part of a token's meaning} -@d hash_base=257 {hashing actually starts here} -@d hash_is_full == (hash_used=hash_base) {are all positions occupied?} -@z -@x module 210 -for j:=0 to l-1 do buffer[j]:=str_pool[k+j]; -cur_sym:=id_lookup(0,l);@/ -if s>=128 then {we don't want to have the string twice} -@y -for j:=0 to l-1 do buffer[j]:=so(str_pool[k+j]); -cur_sym:=id_lookup(0,l);@/ -if s>=256 then {we don't want to have the string twice} -@z -@x module 223 -begin c:=char_class[str_pool[str_start[r]]]; -@y -begin c:=char_class[so(str_pool[str_start[r]])]; -@z -@x module 717 - begin buffer[first]:=str_pool[j]; incr(j); incr(first); -@y - begin buffer[first]:=so(str_pool[j]); incr(j); incr(first); -@z -@x module 774 -for j:=str_start[a] to str_start[a+1]-1 do append_to_name(str_pool[j]); -for j:=str_start[n] to str_start[n+1]-1 do append_to_name(str_pool[j]); -for j:=str_start[e] to str_start[e+1]-1 do append_to_name(str_pool[j]); -@y -for j:=str_start[a] to str_start[a+1]-1 do append_to_name(so(str_pool[j])); -for j:=str_start[n] to str_start[n+1]-1 do append_to_name(so(str_pool[j])); -for j:=str_start[e] to str_start[e+1]-1 do append_to_name(so(str_pool[j])); -@z -@x module 912 - else begin cur_exp:=round_unscaled(cur_exp) mod 128; cur_type:=string_type; - if cur_exp<0 then cur_exp:=cur_exp+128; -@y - else begin cur_exp:=round_unscaled(cur_exp) mod 256; cur_type:=string_type; - if cur_exp<0 then cur_exp:=cur_exp+256; -@z -@x module 913 - else n:=str_pool[str_start[cur_exp]] -@y - else n:=so(str_pool[str_start[cur_exp]]) -@z -@x ibid - begin m:=str_pool[k]; -@y - begin m:=so(str_pool[k]); -@z -@x module 976 -for k:=str_start[a] to str_start[a+1]-1 do append_char(str_pool[k]); -for k:=str_start[b] to str_start[b+1]-1 do append_char(str_pool[k]); -@y -for k:=str_start[a] to str_start[a+1]-1 do append_char(so(str_pool[k])); -for k:=str_start[b] to str_start[b+1]-1 do append_char(so(str_pool[k])); -@z -@x module 977 - for k:=str_start[s]+b-1 downto str_start[s]+a do append_char(str_pool[k]) -else for k:=str_start[s]+a to str_start[s]+b-1 do append_char(str_pool[k]); -@y - for k:=str_start[s]+b-1 downto str_start[s]+a do append_char(so(str_pool[k])) -else for k:=str_start[s]+a to str_start[s]+b-1 do append_char(so(str_pool[k])); -@z -@x module 1103 - begin c:=str_pool[str_start[cur_exp]]; goto found; -@y - begin c:=so(str_pool[str_start[cur_exp]]); goto found; -@z -@x module 1160 - for k:=str_start[s] to str_start[s+1]-1 do gf_out(str_pool[k]); - end; -if t<>0 then for k:=str_start[t] to str_start[t+1]-1 do gf_out(str_pool[k]); -@y - for k:=str_start[s] to str_start[s+1]-1 do gf_out(so(str_pool[k])); - end; -if t<>0 then for k:=str_start[t] to str_start[t+1]-1 do gf_out(so(str_pool[k])); -@z -@x module 1192 - w.b0:=str_pool[k]; w.b1:=str_pool[k+1]; - w.b2:=str_pool[k+2]; w.b3:=str_pool[k+3]; -@y [often qi(so(x))=x, but not e.g. when "quarterwords" are two bytes] - w.b0:=qi(so(str_pool[k])); w.b1:=qi(so(str_pool[k+1])); - w.b2:=qi(so(str_pool[k+2])); w.b3:=qi(so(str_pool[k+3])); -@z -@x module 1193 - str_pool[k]:=w.b0; str_pool[k+1]:=w.b1; - str_pool[k+2]:=w.b2; str_pool[k+3]:=w.b3 -@y - str_pool[k]:=si(qo(w.b0)); str_pool[k+1]:=si(qo(w.b1)); - str_pool[k+2]:=si(qo(w.b2)); str_pool[k+3]:=si(qo(w.b3)) -@z - -549. Make ".base" more easily switchable (see TeX82 log #369). -@x module 775 gets a new definition -@y -@d base_extension=".base" {the extension, as a \.{WEB} constant} -@z now replace ".base" by base_extension in modules 784 and 1200. - -550. "This can't happen" happened because of nonmonotonic rounding - (bug found by Mark Eklof, fixed 7 Oct 89) -@x module 411 -left_x(r):=x_coord(r); -@y -left_x(r):=x_coord(r); -if right_x(p)>x_coord(r) then right_x(p):=x_coord(r); - {we always have |x_coord(p)<=right_x(p)|} -@z -@x ibid -else if x_coord(r)>dest_x then x_coord(r):=dest_x; -@y -else begin if x_coord(r)>dest_x then - begin x_coord(r):=dest_x; left_x(r):=-x_coord(r); right_x(r):=x_coord(r); - end; - if left_x(q)>dest_x then left_x(q):=dest_x - else if left_x(q)x_coord(s) then left_x(q):=-x_coord(s) -else negate(left_x(q)); -negate(x_coord(s)); right_x(s):=x_coord(s); -@z -@x module 415 -if x_coord(r)>dest_x then x_coord(r):=dest_x -else if x_coord(r)y_coord(r) then right_y(pp):=y_coord(r); - {we always have |y_coord(pp)<=right_y(pp)|} -@z -@x ibid -else if y_coord(r)>dest_y then y_coord(r):=dest_y; -@y -else begin if y_coord(r)>dest_y then - begin y_coord(r):=dest_y; left_y(r):=-y_coord(r); right_y(r):=y_coord(r); - end; - if left_y(qq)>dest_y then left_y(qq):=dest_y - else if left_y(qq)dest_x then x_coord(s):=dest_x -else if x_coord(s)y_coord(s) then left_y(qq):=-y_coord(s) -else negate(left_y(qq)); -negate(y_coord(s)); right_y(s):=y_coord(s); -@z -@x module 424 -if y_coord(r)>dest_y then y_coord(r):=dest_y -else if y_coord(r)dest_x+dest_y then - begin y_coord(r):=dest_x+dest_y-x_coord(p); - if left_y(r)>y_coord(r) then - begin left_y(r):=y_coord(r); - if right_y(p)>y_coord(r) then right_y(p):=y_coord(r); - end; - end; -if x_coord(r)dest_x+dest_y then - x_coord(r):=dest_x+dest_y-y_coord(r); -left_x(r):=x_coord(r); -if right_x(p)>x_coord(r) then right_x(p):=x_coord(r); - {we always have |x_coord(p)<=right_x(p)|} -y_coord(r):=y_coord(r)+x_coord(r); right_y(r):=right_y(r)+x_coord(r);@/ -negate(x_coord(r)); right_x(r):=x_coord(r);@/ -left_y(q):=left_y(q)+left_x(q); negate(left_x(q));@/ -dest_y:=dest_y+dest_x; negate(dest_x); -if right_y(r)>dest_y then right_y(r):=dest_y; -if left_y(q)>dest_y then left_y(q):=dest_y -else if left_y(q)left_y(q) then right_y(r):=left_y(q); -@z -@x ibid -else if x_coord(r)>dest_x then x_coord(r):=dest_x -@y -else begin if x_coord(r)>dest_x then - begin x_coord(r):=dest_x; left_x(r):=-x_coord(r); right_x(r):=x_coord(r); - end; - if left_x(q)>dest_x then left_x(q):=dest_x - else if left_x(q)= -begin split_cubic(r,t,dest_x,dest_y); s:=link(r);@/ -if x_coord(r)+y_coord(s)>dest_x+dest_y then - begin y_coord(s):=dest_x+dest_y-x_coord(r); - if left_y(s)>y_coord(s) then - begin left_y(s):=y_coord(s); - if right_y(r)>y_coord(s) then right_y(r):=y_coord(s); - end; - end; -if x_coord(s)+y_coord(s)>dest_x+dest_y then x_coord(s):=dest_x+dest_y-y_coord(s) -else begin if x_coord(s)x_coord(s) then - begin left_y(q):=left_y(q)+x_coord(s); left_x(q):=-x_coord(s);@+end -else begin left_y(q):=left_y(q)+left_x(q); negate(left_x(q));@+end; -y_coord(s):=y_coord(s)+x_coord(s); right_y(s):=right_y(s)+x_coord(s);@/ -negate(x_coord(s)); right_x(s):=x_coord(s);@/ -dest_y:=dest_y+dest_x; -if right_y(s)>dest_y then right_y(s):=dest_y; -if left_y(q)>dest_y then left_y(q):=dest_y -else if left_y(q)left_y(q) then right_y(s):=left_y(q); -end -@z - -551. Major change for extended ligatures. -@x module 11 (this may affect change files) -@!lig_table_size=300; {maximum number of ligature/kern steps} -@y -@!lig_table_size=5000; {maximum number of ligature/kern steps, must be - at least 255 and at most 32510} -@!max_kerns=500; {maximum number of distinct kern amounts} -@z -@x module 14 gets a new line of code -@y -if(lig_table_size<255)or(lig_table_size>32510)then bad:=7; -@z -@x module 186 -@d lig_kern_token=76 {the operators `\&{kern}' and `\.{=:}'} -@d assignment=77 {the operator `\.{:=}'} -@d colon=78 {the operator `\.:'} -@# -@d comma=79 {the operator `\.,'} -@d end_of_statement==cur_cmd>comma -@d semicolon=80 {the operator `\.;', must be |comma+1|} -@d end_group=81 {end a group (\&{endgroup}), must be |semicolon+1|} -@d stop=82 {end a job (\&{end}, \&{dump}), must be |end_group+1|} -@y -@d lig_kern_token=76 - {the operators `\&{kern}' and `\.{=:}' and `\.{=:\char'174}, etc.} -@d assignment=77 {the operator `\.{:=}'} -@d skip_to=78 {the operation `\&{skipto}'} -@d bchar_label=79 {the operator `\.{\char'174\char'174:}'} -@d double_colon=80 {the operator `\.{::}'} -@d colon=81 {the operator `\.:'} -@# -@d comma=82 {the operator `\.,', must be |colon+1|} -@d end_of_statement==cur_cmd>comma -@d semicolon=83 {the operator `\.;', must be |comma+1|} -@d end_group=84 {end a group (\&{endgroup}), must be |semicolon+1|} -@d stop=85 {end a job (\&{end}, \&{dump}), must be |end_group+1|} -@z -@x module 190 -@d max_given_internal=warning_check -@y -@d boundary_char=41 {the right boundary character for ligatures} -@d max_given_internal=41 -@z -@x module 192 gets two new lines of code -@y -primitive("boundarychar",internal_quantity,boundary_char);@/ -@!@:boundary_char_}{\&{boundarychar} primitive@> -@z -@x and module 193 gets one too -@y -int_name[boundary_char]:="boundarychar"; -@z -@x and module 211 gets several -@y (to be inserted in appropriate places) -primitive("::",double_colon,0); -@!@::: }{\.{::} primitive@> -primitive("||:",bchar_label,0); -@!@:::: }{\.{\char'174\char'174:} primitive@> -primitive("skipto",skip_to,0);@/ -@!@:skip_to_}{\&{skipto} primitive@> -@z -@x as does module 212 -@y -bchar_label:print("||:"); -double_colon:print("::"); -skip_to:print("skipto"); -@z -@x module 1093 has new text (see TeX change 362 for module 545) and also this: -@d stop_bit(#)==lig_kern[#].b0 -@d next_char(#)==lig_kern[#].b1 -@d op_bit(#)==lig_kern[#].b2 -@y -@d skip_byte(#)==lig_kern[#].b0 -@d next_char(#)==lig_kern[#].b1 -@d op_byte(#)==lig_kern[#].b2 -@z -@x module 1096 gets a new definition -@y -@d undefined_label==lig_table_size {an undefined local label} -@z -@x ...and some changed declarations -@!char_remainder:array[eight_bits] of eight_bits; {the |remainder| byte} -@!header_byte:array[1..header_size] of -1..255; - {bytes of the \.{TFM} header, or $-1$ if unset} -@!lig_kern:array[0..lig_table_size] of four_quarters; {the ligature/kern table} -@!nl:0..lig_table_size; {the number of ligature/kern steps so far} -@!kern:array[eight_bits] of scaled; {distinct kerning amounts} -@!nk:0..256; {the number of distinct kerns so far} -@y -@!char_remainder:array[eight_bits] of 0..lig_table_size; {the |remainder| byte} -@!header_byte:array[1..header_size] of -1..255; - {bytes of the \.{TFM} header, or $-1$ if unset} -@!lig_kern:array[0..lig_table_size] of four_quarters; {the ligature/kern table} -@!nl:0..32767-256; {the number of ligature/kern steps so far} -@!kern:array[0..max_kerns] of scaled; {distinct kerning amounts} -@!nk:0..max_kerns; {the number of distinct kerns so far} -@z -@x ...and some new declarations -@y -@!skip_table:array[eight_bits] of 0..lig_table_size; {local label status} -@!lk_started:boolean; {has there been a lig/kern step in this command yet?} -@!bchar:integer; {right boundary character} -@!bch_label:0..lig_table_size; {left boundary starting location} -@!ll,@!lll:0..lig_table_size; {registers used for lig/kern processing} -@!label_loc:array[0..256] of -1..lig_table_size; {lig/kern starting addresses} -@!label_char:array[1..256] of eight_bits; {characters for |label_loc|} -@!label_ptr:0..256; {highest position occupied in |label_loc|} -@z -@x module 1097 - end; -for k:=1 to header_size do header_byte[k]:=-1; -bc:=255; ec:=0; nl:=0; nk:=0; ne:=0; np:=0; -@y - skip_table[k]:=undefined_label; - end; -for k:=1 to header_size do header_byte[k]:=-1; -bc:=255; ec:=0; nl:=0; nk:=0; ne:=0; np:=0;@/ -internal[boundary_char]:=-unity; -bch_label:=undefined_label;@/ -label_loc[0]:=-1; label_ptr:=0; -@z -@x module 1104 -procedure set_tag(@!c:eight_bits;@!t:small_number;@!r:eight_bits); -begin if char_tag[c]=no_tag then - begin char_tag[c]:=t; char_remainder[c]:=r; -@y -procedure set_tag(@!c:halfword;@!t:small_number;@!r:halfword); -begin if char_tag[c]=no_tag then - begin char_tag[c]:=t; char_remainder[c]:=r; - if t=lig_tag then - begin incr(label_ptr); label_loc[label_ptr]:=r; label_char[label_ptr]:=c; - end; -@z -@x module 1105 -if (c>" ")and(c<128) then print(c) -@y -if (c>" ")and(c<127) then print(c) -else if c=256 then print("||") -@z -@x module 1106 -label continue; -var @!c,@!cc:eight_bits; {character codes} -@!k:0..256; {index into the |kern| array} -@y -label continue,done; -var @!c,@!cc:0..256; {character codes} -@!k:0..max_kerns; {index into the |kern| array} -@z -% also the previous code of module 1107 is inserted into 1106 -@x modules 1107--1111 are completely replaced -@y by the following new code: -@ @= -begin lk_started:=false; -continue: get_x_next; -if(cur_cmd=skip_to)and lk_started then - @; -if cur_cmd=bchar_label then - begin c:=256; cur_cmd:=colon;@+end -else begin back_input; c:=get_code;@+end; -if(cur_cmd=colon)or(cur_cmd=double_colon)then - @; -if cur_cmd=lig_kern_token then @ -else begin print_err("Illegal ligtable step"); -@.Illegal ligtable step@> - help1("I was looking for `=:' or `kern' here."); - back_error; next_char(nl):=qi(0); op_byte(nl):=qi(0); rem_byte(nl):=qi(0);@/ - skip_byte(nl):=stop_flag+1; {this specifies an unconditional stop} - end; -if nl=lig_table_size then overflow("ligtable size",lig_table_size); -@:METAFONT capacity exceeded ligtable size}{\quad ligtable size@> -incr(nl); -if cur_cmd=comma then goto continue; -if skip_byte(nl-1)= -primitive("=:",lig_kern_token,0); -@!@:=:_}{\.{=:} primitive@> -primitive("=:|",lig_kern_token,1); -@!@:=:/_}{\.{=:\char'174} primitive@> -primitive("=:|>",lig_kern_token,5); -@!@:=:/>_}{\.{=:\char'174>} primitive@> -primitive("|=:",lig_kern_token,2); -@!@:=:/_}{\.{\char'174=:} primitive@> -primitive("|=:>",lig_kern_token,6); -@!@:=:/>_}{\.{\char'174=:>} primitive@> -primitive("|=:|",lig_kern_token,3); -@!@:=:/_}{\.{\char'174=:\char'174} primitive@> -primitive("|=:|>",lig_kern_token,7); -@!@:=:/>_}{\.{\char'174=:\char'174>} primitive@> -primitive("|=:|>>",lig_kern_token,11); -@!@:=:/>_}{\.{\char'174=:\char'174>>} primitive@> -primitive("kern",lig_kern_token,128); -@!@:kern_}{\&{kern} primitive@> - -@ @= -lig_kern_token: case m of -0:print("=:"); -1:print("=:|"); -2:print("|=:"); -3:print("|=:|"); -5:print("=:|>"); -6:print("|=:>"); -7:print("|=:|>"); -11:print("|=:|>>"); -othercases print("kern") -endcases; - -@ Local labels are implemented by maintaining the |skip_table| array, -where |skip_table[c]| is either |undefined_label| or the address of the -most recent lig/kern instruction that skips to local label~|c|. In the -latter case, the |skip_byte| in that instruction will (temporarily) -be zero if there were no prior skips to this label, or it will be the -distance to the prior skip. - -We may need to cancel skips that span more than 127 lig/kern steps. - -@d cancel_skips(#)==ll:=#; - repeat lll:=qo(skip_byte(ll)); skip_byte(ll):=stop_flag; ll:=ll-lll; - until lll=0 -@d skip_error(#)==begin print_err("Too far to skip"); -@.Too far to skip@> - help1("At most 127 lig/kern steps can separate skipto1 from 1::."); - error; cancel_skips(#); - end - -@= -begin c:=get_code; -if nl-skip_table[c]>128 then {|skip_table[c]<= -begin if cur_cmd=colon then - if c=256 then bch_label:=nl - else set_tag(c,lig_tag,nl) -else if skip_table[c]128 then - begin skip_error(ll); goto continue; - end; - skip_byte(ll):=qi(nl-ll-1); ll:=ll-lll; - until lll=0; - end; -goto continue; -end -@x module 1112 -next_char(nl):=qi(c); op_bit(nl):=qi(cur_mod); stop_bit(nl):=qi(0); -if cur_mod=0 then rem_byte(nl):=qi(get_code) -@y -begin next_char(nl):=qi(c); skip_byte(nl):=qi(0); -if cur_mod<128 then {ligature op} - begin op_byte(nl):=qi(cur_mod); rem_byte(nl):=qi(get_code); - end -@z -@x ibid - begin if nk=256 then overflow("kern",256); -@:METAFONT capacity exceeded kern}{\quad kern@> - incr(nk); - end; - rem_byte(nl):=qi(k); - end -@y - begin if nk=max_kerns then overflow("kern",max_kerns); -@:METAFONT capacity exceeded kern}{\quad kern@> - incr(nk); - end; - op_byte(nl):=kern_flag+(k div 256); - rem_byte(nl):=qi((k mod 256)); - end; -lk_started:=true; -end -@z -@x module 1135 -tfm_two(6+lh+(ec-bc+1)+nw+nh+nd+ni+nl+nk+ne+np); - {this is the total number of file words that will be output} -tfm_two(lh); tfm_two(bc); tfm_two(ec); tfm_two(nw); tfm_two(nh); -tfm_two(nd); tfm_two(ni); tfm_two(nl); tfm_two(nk); tfm_two(ne); tfm_two(np); -@y -@; -tfm_two(6+lh+(ec-bc+1)+nw+nh+nd+ni+nl+lk_offset+nk+ne+np); - {this is the total number of file words that will be output} -tfm_two(lh); tfm_two(bc); tfm_two(ec); tfm_two(nw); tfm_two(nh); -tfm_two(nd); tfm_two(ni); tfm_two(nl+lk_offset); tfm_two(nk); tfm_two(ne); -tfm_two(np); -@z -% modules 1137&1138 are combined into a single module -% and so are modules 1140--1141, to make room for two new modules. -@x module 1136 is moved to after old module 1141 -@y and changed to the following code: -@ @= -if bch_label= -bchar:=round_unscaled(internal[boundary_char]); -if(bchar<0)or(bchar>255)then - begin bchar:=-1; lk_started:=false; lk_offset:=0;@+end -else begin lk_started:=true; lk_offset:=1;@+end; -@; -if bch_label= -k:=label_ptr; {pointer to the largest unallocated label} -if label_loc[k]+lk_offset>255 then - begin lk_offset:=0; lk_started:=false; {location 0 can do double duty} - repeat char_remainder[label_char[k]]:=lk_offset; - while label_loc[k-1]=label_loc[k] do - begin decr(k); char_remainder[label_char[k]]:=lk_offset; - end; - incr(lk_offset); decr(k); - until lk_offset+label_loc[k]<256; - {N.B.: |lk_offset=256| satisfies this when |k=0|} - end; -if lk_offset>0 then - while k>0 do - begin char_remainder[label_char[k]] - :=char_remainder[label_char[k]]+lk_offset; - decr(k); - end - -@ @= -for k:=0 to 255 do if skip_table[k] - cancel_skips(skip_table[k]); - end; -if lk_started then {|lk_offset=1| for the special |bchar|} - begin tfm_out(255); tfm_out(bchar); tfm_two(0); - end -else for k:=1 to lk_offset do {output the redirection specs} - begin ll:=label_loc[label_ptr]; - if bchar<0 then - begin tfm_out(254); tfm_out(0); - end - else begin tfm_out(255); tfm_out(bchar); - end; - tfm_two(ll+lk_offset); - repeat decr(label_ptr); - until label_loc[label_ptr]token_list then - @ -else begin lhs:=cur_exp; cur_path_type:=cur_mod;@/ - cur_type:=vacuous; get_x_next; scan_expression; - if cur_path_type=also_code then @ -@y -@!add_to_type:double_path_code..also_code; {modifier of \&{addto}} -begin get_x_next; var_flag:=thing_to_add; scan_primary; -if cur_type<>token_list then - @ -else begin lhs:=cur_exp; add_to_type:=cur_mod;@/ - cur_type:=vacuous; get_x_next; scan_expression; - if add_to_type=also_code then @ -@z -@x module 1064 -else begin lhs:=null; -@y -else begin lhs:=null; cur_path_type:=add_to_type; -@z - -554. Balance the parens showing on the terminal (for Lispers). -@x module 631 -@!in_open : 0..max_in_open; {the number of lines in the buffer, less one} -@y -@!in_open : 0..max_in_open; {the number of lines in the buffer, less one} -@!open_parens : 0..max_in_open; {the number of open text files} -@z -@x module 657 -in_open:=0; max_buf_stack:=0; -@y -in_open:=0; open_parens:=0; max_buf_stack:=0; -@z -@x module 681 - begin print_char(")"); force_eof:=false; - update_terminal; {show user that file has been read} -@y - begin print_char(")"); decr(open_parens); - update_terminal; {show user that file has been read} - force_eof:=false; -@z -@x module 793 -print_char("("); print(name); update_terminal; -@y -print_char("("); incr(open_parens); print(name); update_terminal; -@z -@x module 1209 -if job_name=0 then open_log_file; -@y -if job_name=0 then open_log_file; -while open_parens>0 do - begin print(" )"); decr(open_parens); - end; -@z - ------------Here I draw the line with respect to further changes - -555. Don't try system area if an area was given (see tex82.bug number 312; -found by Jonathan Kew, May 1990) -@x module 793 - pack_file_name(cur_name,MF_area,cur_ext); - if a_open_in(cur_file) then goto done; -@y - if cur_area="" then - begin pack_file_name(cur_name,MF_area,cur_ext); - if a_open_in(cur_file) then goto done; - end; -@z - -556. Report correct line number when buffer overflows (CET, Jul 90). -@x module 794 -begin if not input_ln(cur_file,false) then do_nothing; -firm_up_the_line; -buffer[limit]:="%"; first:=limit+1; loc:=start; line:=1; -@y -begin line:=1; -if input_ln(cur_file,false) then do_nothing; -firm_up_the_line; -buffer[limit]:="%"; first:=limit+1; loc:=start; -@z - -557. TeX82 bug 308, corrected in 1985, is also in MF! (Lutz Birkhahn, May91) -@x module 176 -var_used:=lo_mem_stat_max+1-mem_min; dyn_used:=mem_top+1-hi_mem_stat_min; -@y -var_used:=lo_mem_stat_max+1-mem_min; dyn_used:=mem_top+1-hi_mem_min; -@z - -558. Allow unprintable file names, as in TeX change 396 (19 Sep 91) -(Much of this is redundant except for people who make nonportable -versions that allow other 8-bit codes to be in variable names---and for -those people only if they allow input of more codes than they can print! -Still, it seems best to make the programs for TeX and MF as alike as possible.) -@x module 59 -j:=str_start[s]; -while jpseudo) then print_char(s) -else begin j:=str_start[s]; - while jpseudo) then print_char(s) -else begin j:=str_start[s]; - while jnull then print(text(name)) -@y - if name<>null then slow_print(text(name)) -@z -@x module 664 - if scanner_status=op_defining then print(text(warning_info)) -@y - if scanner_status=op_defining then slow_print(text(warning_info)) -@z -@x module 664 again -loop_defining: begin print("the text of a "); print(text(warning_info)); -@y -loop_defining: begin print("the text of a "); slow_print(text(warning_info)); -@z -@x module 722 -begin if n<>null then print(text(n)) -@y -begin if n<>null then slow_print(text(n)) -@z -@x module 722 again - if p=null then print(text(info(info(link(a))))) -@y - if p=null then slow_print(text(info(info(link(a))))) -@z -@x module 725 - print_nl(" Missing `"); print(text(r_delim)); -@y - print_nl(" Missing `"); slow_print(text(r_delim)); -@z -@x module 773 -begin print(a); print(n); print(e); -@y -begin slow_print(a); slow_print(n); slow_print(e); -@z -@x module 790 -print(base_ident); print(" "); -@y -slow_print(base_ident); print(" "); -@z -@x module 793 -print_char("("); incr(open_parens); print(name); update_terminal; -@y -print_char("("); incr(open_parens); slow_print(name); update_terminal; -@z -@x module 998 -if info(lhs)>hash_end then print(int_name[info(lhs)-(hash_end)]) -@y -if info(lhs)>hash_end then slow_print(int_name[info(lhs)-(hash_end)]) -@z -@x module 999 - print(int_name[info(lhs)-(hash_end)]); -@y - slow_print(int_name[info(lhs)-(hash_end)]); -@z -@x module 1032 -else begin print_err("The token `"); print(text(r_delim)); -@y -else begin print_err("The token `"); slow_print(text(r_delim)); -@z -@x module 1034 - else print(text(cur_sym)); -@y - else slow_print(text(cur_sym)); -@z -@x module 1041 -else begin print(text(cur_sym)); print_char("="); -@y -else begin slow_print(text(cur_sym)); print_char("="); -@z -@x module 1042 -else begin print_char(""""); print(cur_mod); print_char(""""); -@y -else begin print_char(""""); slow_print(cur_mod); print_char(""""); -@z -@x module 1043 - print("t delimiter that matches "); print(text(m)); -@y - print("t delimiter that matches "); slow_print(text(m)); -@z -@x module 1043 again -internal_quantity:print(int_name[m]); -@y -internal_quantity:slow_print(int_name[m]); -@z -@x module 1134 -print_nl("Font metrics written on "); print(metric_file_name); print_char("."); -@y -print_nl("Font metrics written on "); slow_print(metric_file_name); -print_char("."); -@z -@x module 1182 -print_nl("Output written on "); print(output_file_name); -@y -print_nl("Output written on "); slow_print(output_file_name); -@z -@x module 1200 -print(w_make_name_string(base_file)); flush_string(str_ptr-1); -print_nl(base_ident) -@y -slow_print(w_make_name_string(base_file)); flush_string(str_ptr-1); -print_nl(""); slow_print(base_ident) -@z -@x module 1205 - print(log_name); print_char("."); -@y - slow_print(log_name); print_char("."); -@z -@x module 1213 -10: print(n); -@y -10: slow_print(n); -@z - ------- The third printing of Volume D (October 1991) incorporated the above. - -559. Debugging routine never used since change 528; needed update then (JDH). -@x module 617 - p:=dep_list(p); r:=hi_mem_min; - repeat if info(p)>=r then -@y - p:=dep_list(p); r:=inf_val; - repeat if value(info(p))>=value(r) then -@z - -560. Corrections to blunders in change 550 (noted by B Jackowski, Jul 91). -@x module 415 can use more paranoia even though no problems have occurred yet -negate(left_y(qq)); negate(dest_y);@/ -@y -negate(left_y(qq)); negate(dest_y);@/ -if x_coord(r)dest_x then x_coord(r):=dest_x; -if left_x(r)>x_coord(r) then - begin left_x(r):=x_coord(r); - if right_x(pp)>x_coord(r) then right_x(pp):=x_coord(r); - end; -if right_x(r)dest_x then x_coord(s):=dest_x; -if left_x(s)>x_coord(s) then - begin left_x(s):=x_coord(s); - if right_x(r)>x_coord(s) then right_x(r):=x_coord(s); - end; -if right_x(s)dest_x+dest_y then - begin y_coord(r):=dest_x+dest_y-x_coord(p); - if left_y(r)>y_coord(r) then - begin left_y(r):=y_coord(r); - if right_y(p)>y_coord(r) then right_y(p):=y_coord(r); - end; - end; -@y -if y_coord(r)dest_y then y_coord(r):=dest_y; -if x_coord(p)+y_coord(r)>dest_x+dest_y then - y_coord(r):=dest_x+dest_y-x_coord(p); -if left_y(r)>y_coord(r) then - begin left_y(r):=y_coord(r); - if right_y(p)>y_coord(r) then right_y(p):=y_coord(r); - end; -if right_y(r)dest_y then right_y(r):=dest_y; -if left_y(q)>dest_y then left_y(q):=dest_y -else if left_y(q)left_y(q) then right_y(r):=left_y(q); -@y -if right_y(r)dest_x+dest_y then - begin y_coord(s):=dest_x+dest_y-x_coord(r); - if left_y(s)>y_coord(s) then - begin left_y(s):=y_coord(s); - if right_y(r)>y_coord(s) then right_y(r):=y_coord(s); - end; - end; -@y -if y_coord(s)dest_y then y_coord(s):=dest_y; -if x_coord(r)+y_coord(s)>dest_x+dest_y then - y_coord(s):=dest_x+dest_y-x_coord(r); -if left_y(s)>y_coord(s) then - begin left_y(s):=y_coord(s); - if right_y(r)>y_coord(s) then right_y(r):=y_coord(s); - end; -if right_y(s)dest_y then right_y(s):=dest_y; -if left_y(q)>dest_y then left_y(q):=dest_y -else if left_y(q)left_y(q) then right_y(s):=left_y(q); -@y -if right_y(s)=fraction_one)or@| - (max_c[dependent] div @'10000 >= max_c[proto_dependent]) then -@y -begin if (max_c[dependent] div @'10000 >= - max_c[proto_dependent]) then -@z - -562. final cleanup should not retain spurious reference counts (20 Mar 95) -@x module 1209 -while open_parens>0 do -@y -while input_ptr>0 do - if token_state then end_token_list@+else end_file_reading; -while loop_ptr<>null do stop_iteration; -while open_parens>0 do -@z -@x module 1209 - cur_if:=name_type(cond_ptr); cond_ptr:=link(cond_ptr); -@y - cur_if:=name_type(cond_ptr); loop_ptr:=cond_ptr; - cond_ptr:=link(cond_ptr); free_node(loop_ptr,if_node_size); -@z - -563. unprintable strings of length 1 need to be truly length 1 (27 Nov 95, -pointed out by Ulrik Vieth) -@x module 671 - if loc=k+1 then cur_mod:=buffer[k] -@y - if (loc=k+1) and (length(buffer[k])=1) then cur_mod:=buffer[k] -@z - -564. minor improvement to pythagorean addition (22 Jan 97) -@x module 124 -if a>0 then -@y -if b>0 then -@z - -565. we need not raise hackles about two-digit years (23 Nov 98) -@x module 1200 -print_int(round_unscaled(internal[year]) mod 100); print_char("."); -@y -print_int(round_unscaled(internal[year])); print_char("."); -@z - -566. "this can't happen" can happen if coordinates are half vast - (Julian Gilbey, January 2001) -@x module 402 -@!chopped:boolean; {have we truncated any of the data?} -@y -@!chopped:integer; {positive if data truncated, - negative if data dangerously large} -@z -@x module 402 -if internal[autorounding]>0 then xy_round; -octant_subdivide; {complete the subdivision} -if internal[autorounding]>unity then diag_round; -@; -@; -while left_type(cur_spec)<>endpoint do cur_spec:=link(cur_spec); -if tracing>0 then - if internal[autorounding]<=0 then print_spec(", after subdivision") -@y -if (internal[autorounding]>0)and(chopped=0) then xy_round; -octant_subdivide; {complete the subdivision} -if (internal[autorounding]>unity)and(chopped=0) then diag_round; -@; -@; -while left_type(cur_spec)<>endpoint do cur_spec:=link(cur_spec); -if tracing>0 then - if (internal[autorounding]<=0)or(chopped<>0) then - print_spec(", after subdivision") -@z -@x module 404 -@d procrustes(#)==if abs(#)>max_allowed then - begin chopped:=true; - if #>0 then #:=max_allowed@+else #:=-max_allowed; - end - -@= -p:=cur_spec; k:=1; chopped:=false; -@y -@d procrustes(#)==if abs(#)>=dmax then - if abs(#)>max_allowed then - begin chopped:=1; - if #>0 then #:=max_allowed@+else #:=-max_allowed; - end - else if chopped=0 then chopped:=-1 - -@= -p:=cur_spec; k:=1; chopped:=0; dmax:=half(max_allowed); -@z -@x module 404 -if chopped then -@y -if chopped>0 then -@z - -567. I forgot to update curtype in e.g. boolean b[]; b1=true=b2; - (Thorsten Dahlheimer, June 2004) -@x 1003 - begin nonlinear_eq(v,cur_exp,false); goto done; -@y - begin nonlinear_eq(v,cur_exp,false); unstash_cur_exp(cur_exp); goto done; -@z - -568. Wrong handling of extreme TFM values (T. Dahlheimer, June 2004) -@x 1128 -max_tfm_dimen:=16*internal[design_size]-internal[design_size] div @'10000000; -@y -max_tfm_dimen:=16*internal[design_size]-1-internal[design_size] div @'10000000; -@z -@x 1129 - if x>0 then x:=three_bytes-1@+else x:=1-three_bytes; - end -else x:=make_scaled(x*16,internal[design_size]); -@y - if x>0 then x:=max_tfm_param@+else x:=-max_tfm_param; - end; -x:=make_scaled(x*16,internal[design_size]); -@z - -569. Bug in make_ellipse when theta=180 (T. Dahlheimer, June 2004) -@x 530 - else begin beta:=minor_axis; gamma:=major_axis; -@y - else begin beta:=minor_axis; gamma:=major_axis; theta:=0; -@z - -570. Forgot outer_tag in scan_declared variable (T. Dahlheimer, June 2004) -@x 1011 -done: if eq_type(x)<>tag_token then clear_symbol(x,false); -@y -done: if eq_type(x) mod outer_tag<>tag_token then clear_symbol(x,false); -@z - -571. Apparent bug if init_gf called at incredibly unlikely time (T. Dahlheimer, -June 2004); not REALLY a bug, because str_ptr cannot equal max_strings here -(because this was checked by end_name, and area_delimiter=0 there because -cur_area="" in the output file name); but anyway I'll make a patch to be clean -@x 1163 -str_start[str_ptr+1]:=pool_ptr; gf_string(0,str_ptr); -@y -gf_string(0,make_string); decr(str_ptr); -@z - -572. Memory leak in make_ellipse on symmetric pens that don't have -a point on the x-axis (Eberhard Mattes, 03 June 2008) -@x module 536 -done1: link(p):=s; beta:=-y_coord(h); -@y -done1: if (link(p)<>null) then free_node(link(p),knot_node_size); -link(p):=s; beta:=-y_coord(h); -@z - -573. Don't restrict the length of the banner line, leave it system-dependent code -(Udo Wermuth, 02 April 2017) -@x module 61 -incorrect, but the discrepancy is not serious since we assume that the banner -and base identifier together will occupy at most |max_print_line| -character positions. -@y -incorrect, but the discrepancy is not serious since we assume that this -part of the program is system dependent. -@^system dependencies@> -@z - -574. Defeat interactions during batch mode (Xiaosa Zhang, 27 June 2020) -@x module 78 -@ @= -loop@+begin continue: clear_for_error_prompt; prompt_input("? "); -@y -@ @= -loop@+begin continue: if interaction<>error_stop_mode then return; - clear_for_error_prompt; prompt_input("? "); -@z - -575. Don't exit to editor if no input file is at the bottom line -(Xiaosa Zhang, 03 July 2020) -@x module 79 -"E": if file_ptr>0 then -@y -"E": if file_ptr>0 then if input_stack[file_ptr].name_field>=256 then -@z -@x module 80 -if file_ptr>0 then print("E to edit your file,"); -@y -if file_ptr>0 then if input_stack[file_ptr].name_field>=256 then - print("E to edit your file,"); -@z - -576. Keep date and time in system variables, use them in opening banner -(Udo Wermuth, 11 December 2020) -@x module 194 -Since standard \PASCAL\ cannot provide such information, something special -is needed. The program here simply specifies July 4, 1776, at noon; but -users probably want a better approximation to the truth. - -Note that the values are |scaled| integers. Hence \MF\ can no longer -be used after the year 32767. - -@p procedure fix_date_and_time; -begin internal[time]:=12*60*unity; {minutes since midnight} -internal[day]:=4*unity; {fourth day of the month} -internal[month]:=7*unity; {seventh month of the year} -internal[year]:=1776*unity; {Anno Domini} -end; -@y -Since standard \PASCAL\ cannot provide such information, something special -is needed. The program here simply assumes that suitable values appear in -the global variables \\{sys\_time}, \\{sys\_day}, \\{sys\_month}, and -\\{sys\_year} (which are initialized to noon on 4 July 1776, -in case the implementor is careless). - -Note that the values are |scaled| integers. Hence \MF\ can no longer -be used after the year 32767. - -@p procedure fix_date_and_time; -begin sys_time:=12*60; -sys_day:=4; sys_month:=7; sys_year:=1776; {self-evident truths} -internal[time]:=sys_time*unity; {minutes since midnight} -internal[day]:=sys_day*unity; {day of the month} -internal[month]:=sys_month*unity; {month of the year} -internal[year]:=sys_year*unity; {Anno Domini} -end; -@z -@x module 196 -@ Of course we had better declare another global variable, if the previous -routines are going to work. - -@= -@!old_setting:0..max_selector; -@y -@ Of course we had better declare a few more global variables, if the previous -routines are going to work. - -@= -@!old_setting:0..max_selector; -@!sys_time,@!sys_day,@!sys_month,@!sys_year:integer; - {date and time supplied by external system} -@z -@x module 790 -print_int(round_unscaled(internal[day])); print_char(" "); -months:='JANFEBMARAPRMAYJUNJULAUGSEPOCTNOVDEC'; -m:=round_unscaled(internal[month]); -for k:=3*m-2 to 3*m do wlog(months[k]); -print_char(" "); print_int(round_unscaled(internal[year])); print_char(" "); -m:=round_unscaled(internal[time]); -print_dd(m div 60); print_char(":"); print_dd(m mod 60); -@y -print_int(sys_day); print_char(" "); -months:='JANFEBMARAPRMAYJUNJULAUGSEPOCTNOVDEC'; -for k:=3*sys_month-2 to 3*sys_month do wlog(months[k]); -print_char(" "); print_int(sys_year); print_char(" "); -print_dd(sys_time div 60); print_char(":"); print_dd(sys_time mod 60); -@z -@x module 1211 -fix_date_and_time; init_randoms((internal[time] div unity)+internal[day]);@/ -@y -fix_date_and_time; init_randoms(sys_time+sys_day*unity);@/ -@z - -------------- -999. The absolutely final change (to be made after my death) -@x module 2 -@d banner=='This is METAFONT, Version 2.71828182' {printed when \MF\ starts} -@y -@d banner=='This is METAFONT, Version $e$' {printed when \MF\ starts} -@z -When this change is made, the corresponding line should be changed in -Volume D, and also on page 31 of The METAFONTbook. -My last will and testament for METAFONT is that no further changes be made -under any circumstances. Improved systems should not be called simply -`METAFONT'; that name, unqualified, should refer only to the program for which -I have taken personal responsibility. -- Don Knuth -- cgit v1.2.3