|
|
1.1 root 1: /* Merge parameters into a termcap entry string.
2: Copyright (C) 1985, 1987 Free Software Foundation, Inc.
3:
4:
5: NO WARRANTY
6:
7: BECAUSE THIS PROGRAM IS LICENSED FREE OF CHARGE, WE PROVIDE ABSOLUTELY
8: NO WARRANTY, TO THE EXTENT PERMITTED BY APPLICABLE STATE LAW. EXCEPT
9: WHEN OTHERWISE STATED IN WRITING, FREE SOFTWARE FOUNDATION, INC,
10: RICHARD M. STALLMAN AND/OR OTHER PARTIES PROVIDE THIS PROGRAM "AS IS"
11: WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
12: BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
13: FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY
14: AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE
15: DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR
16: CORRECTION.
17:
18: IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW WILL RICHARD M.
19: STALLMAN, THE FREE SOFTWARE FOUNDATION, INC., AND/OR ANY OTHER PARTY
20: WHO MAY MODIFY AND REDISTRIBUTE THIS PROGRAM AS PERMITTED BELOW, BE
21: LIABLE TO YOU FOR DAMAGES, INCLUDING ANY LOST PROFITS, LOST MONIES, OR
22: OTHER SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
23: USE OR INABILITY TO USE (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR
24: DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY THIRD PARTIES OR
25: A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS) THIS
26: PROGRAM, EVEN IF YOU HAVE BEEN ADVISED OF THE POSSIBILITY OF SUCH
27: DAMAGES, OR FOR ANY CLAIM BY ANY OTHER PARTY.
28:
29: GENERAL PUBLIC LICENSE TO COPY
30:
31: 1. You may copy and distribute verbatim copies of this source file
32: as you receive it, in any medium, provided that you conspicuously and
33: appropriately publish on each copy a valid copyright notice "Copyright
34: (C) 1986 Free Software Foundation, Inc."; and include following the
35: copyright notice a verbatim copy of the above disclaimer of warranty
36: and of this License. You may charge a distribution fee for the
37: physical act of transferring a copy.
38:
39: 2. You may modify your copy or copies of this source file or
40: any portion of it, and copy and distribute such modifications under
41: the terms of Paragraph 1 above, provided that you also do the following:
42:
43: a) cause the modified files to carry prominent notices stating
44: that you changed the files and the date of any change; and
45:
46: b) cause the whole of any work that you distribute or publish,
47: that in whole or in part contains or is a derivative of this
48: program or any part thereof, to be licensed at no charge to all
49: third parties on terms identical to those contained in this
50: License Agreement (except that you may choose to grant more extensive
51: warranty protection to some or all third parties, at your option).
52:
53: c) You may charge a distribution fee for the physical act of
54: transferring a copy, and you may at your option offer warranty
55: protection in exchange for a fee.
56:
57: Mere aggregation of another unrelated program with this program (or its
58: derivative) on a volume of a storage or distribution medium does not bring
59: the other program under the scope of these terms.
60:
61: 3. You may copy and distribute this program (or a portion or derivative
62: of it, under Paragraph 2) in object code or executable form under the terms
63: of Paragraphs 1 and 2 above provided that you also do one of the following:
64:
65: a) accompany it with the complete corresponding machine-readable
66: source code, which must be distributed under the terms of
67: Paragraphs 1 and 2 above; or,
68:
69: b) accompany it with a written offer, valid for at least three
70: years, to give any third party free (except for a nominal
71: shipping charge) a complete machine-readable copy of the
72: corresponding source code, to be distributed under the terms of
73: Paragraphs 1 and 2 above; or,
74:
75: c) accompany it with the information you received as to where the
76: corresponding source code may be obtained. (This alternative is
77: allowed only for noncommercial distribution and only if you
78: received the program in object code or executable form alone.)
79:
80: For an executable file, complete source code means all the source code for
81: all modules it contains; but, as a special exception, it need not include
82: source code for modules which are standard libraries that accompany the
83: operating system on which the executable file runs.
84:
85: 4. You may not copy, sublicense, distribute or transfer this program
86: except as expressly provided under this License Agreement. Any attempt
87: otherwise to copy, sublicense, distribute or transfer this program is void and
88: your rights to use the program under this License agreement shall be
89: automatically terminated. However, parties who have received computer
90: software programs from you with this License Agreement will not have
91: their licenses terminated so long as such parties remain in full compliance.
92:
93: 5. If you wish to incorporate parts of this program into other free
94: programs whose distribution conditions are different, write to the Free
95: Software Foundation at 675 Mass Ave, Cambridge, MA 02139. We have not yet
96: worked out a simple rule that can be stated here, but we will often permit
97: this. We will be guided by the two goals of preserving the free status of
98: all derivatives of our free software and of promoting the sharing and reuse of
99: software.
100:
101:
102: In other words, you are welcome to use, share and improve this program.
103: You are forbidden to forbid anyone else to use, share and improve
104: what you give them. Help stamp out software-hoarding! */
105:
106:
107: /* config.h may rename various library functions such as malloc. */
108: #ifdef emacs
109: #include "config.h"
110: #endif
111:
112: /* Assuming STRING is the value of a termcap string entry
113: containing `%' constructs to expand parameters,
114: merge in parameter values and store result in block OUTSTRING points to.
115: LEN is the length of OUTSTRING. If more space is needed,
116: a block is allocated with `malloc'.
117:
118: The value returned is the address of the resulting string.
119: This may be OUTSTRING or may be the address of a block got with `malloc'.
120: In the latter case, the caller must free the block.
121:
122: The fourth and following args to tparam serve as the parameter values. */
123:
124: static char *tparam1 ();
125:
126: /* VARARGS 2 */
127: char *
128: tparam (string, outstring, len, arg0, arg1, arg2, arg3)
129: char *string;
130: char *outstring;
131: int len;
132: int arg0, arg1, arg2, arg3;
133: {
134: #ifdef NO_ARG_ARRAY
135: int arg[4];
136: arg[0] = arg0;
137: arg[1] = arg1;
138: arg[2] = arg2;
139: arg[3] = arg3;
140: return tparam1 (string, outstring, len, 0, 0, arg);
141: #else
142: return tparam1 (string, outstring, len, 0, 0, &arg0);
143: #endif
144: }
145:
146: char *BC;
147: char *UP;
148:
149: static char tgoto_buf[50];
150:
151: char *
152: tgoto (cm, hpos, vpos)
153: char *cm;
154: int hpos, vpos;
155: {
156: int args[2];
157: if (!cm)
158: return 0;
159: args[0] = vpos;
160: args[1] = hpos;
161: return tparam1 (cm, tgoto_buf, 50, UP, BC, args);
162: }
163:
164: static char *
165: tparam1 (string, outstring, len, up, left, argp)
166: char *string;
167: char *outstring;
168: int len;
169: char *up, *left;
170: register int *argp;
171: {
172: register int c;
173: register char *p = string;
174: register char *op = outstring;
175: char *outend;
176: int outlen = 0;
177:
178: register int tem;
179: int *oargp = argp;
180: int doleft = 0;
181: int doup = 0;
182:
183: outend = outstring + len;
184:
185: while (1)
186: {
187: /* If the buffer might be too short, make it bigger. */
188: if (op + 5 >= outend)
189: {
190: register char *new;
191: if (outlen == 0)
192: {
193: new = (char *) malloc (outlen = 40 + len);
194: outend += 40;
195: bcopy (outstring, new, op - outstring);
196: }
197: else
198: {
199: outend += outlen;
200: new = (char *) realloc (outstring, outlen *= 2);
201: }
202: op += new - outstring;
203: outend += new - outstring;
204: outstring = new;
205: }
206: if (!(c = *p++))
207: break;
208: if (c == '%')
209: {
210: c = *p++;
211: tem = *argp;
212: switch (c)
213: {
214: case 'd': /* %d means output in decimal */
215: if (tem < 10)
216: goto onedigit;
217: if (tem < 100)
218: goto twodigit;
219: case '3': /* %3 means output in decimal, 3 digits. */
220: if (tem > 999)
221: {
222: *op++ = tem / 1000 + '0';
223: tem %= 1000;
224: }
225: *op++ = tem / 100 + '0';
226: case '2': /* %2 means output in decimal, 2 digits. */
227: twodigit:
228: tem %= 100;
229: *op++ = tem / 10 + '0';
230: onedigit:
231: *op++ = tem % 10 + '0';
232: argp++;
233: break;
234:
235: case 'C':
236: /* For c-100: print quotient of value by 96, if nonzero,
237: then do like %+ */
238: if (tem >= 96)
239: {
240: *op++ = tem / 96;
241: tem %= 96;
242: }
243: case '+': /* %+x means add character code of char x */
244: tem += *p++;
245: case '.': /* %. means output as character */
246: if (left)
247: {
248: /* If want to forbid output of 0 and \n and \t,
249: and this is one of them, increment it. */
250: while (tem == 0 || tem == '\n' || tem == '\t')
251: {
252: tem++;
253: if (argp == oargp)
254: doup++, outend -= strlen (up);
255: else
256: doleft++, outend -= strlen (left);
257: }
258: }
259: *op++ = tem | 0200;
260: case 'f': /* %f means discard next arg */
261: argp++;
262: break;
263:
264: case 'b': /* %b means back up one arg (and re-use it) */
265: argp--;
266: break;
267:
268: case 'r': /* %r means interchange following two args */
269: argp[0] = argp[1];
270: argp[1] = tem;
271: oargp++;
272: break;
273:
274: case '>': /* %>xy means if arg is > char code of x, */
275: if (argp[0] > *p++) /* then add char code of y to the arg, */
276: argp[0] += *p; /* and in any case don't output. */
277: p++; /* Leave the arg to be output later. */
278: break;
279:
280: case 'a': /* %a means arithmetic */
281: /* Next character says what operation.
282: Add or subtract either a constant or some other arg */
283: /* First following character is + to add or - to subtract
284: or = to assign. */
285: /* Next following char is 'p' and an arg spec
286: (0100 plus position of that arg relative to this one)
287: or 'c' and a constant stored in a character */
288: tem = p[2] & 0177;
289: if (p[1] == 'p')
290: tem = argp[tem - 0100];
291: if (p[0] == '-')
292: argp[0] -= tem;
293: else if (p[0] == '+')
294: argp[0] += tem;
295: else if (p[0] == '*')
296: argp[0] *= tem;
297: else if (p[0] == '/')
298: argp[0] /= tem;
299: else
300: argp[0] = tem;
301:
302: p += 3;
303: break;
304:
305: case 'i': /* %i means add one to arg, */
306: argp[0] ++; /* and leave it to be output later. */
307: argp[1] ++; /* Increment the following arg, too! */
308: break;
309:
310: case '%': /* %% means output %; no arg. */
311: goto ordinary;
312:
313: case 'n': /* %n means xor each of next two args with 140 */
314: argp[0] ^= 0140;
315: argp[1] ^= 0140;
316: break;
317:
318: case 'm': /* %m means xor each of next two args with 177 */
319: argp[0] ^= 0177;
320: argp[1] ^= 0177;
321: break;
322:
323: case 'B': /* %B means express arg as BCD char code. */
324: argp[0] += 6 * (tem / 10);
325: break;
326:
327: case 'D': /* %D means weird Delta Data transformation */
328: argp[0] -= 2 * (tem % 16);
329: break;
330: }
331: }
332: else
333: /* Ordinary character in the argument string. */
334: ordinary:
335: *op++ = c;
336: }
337: *op = 0;
338: while (doup-- > 0)
339: strcat (op, up);
340: while (doleft-- > 0)
341: strcat (op, left);
342: return outstring;
343: }
344:
345: #ifdef DEBUG
346:
347: main (argc, argv)
348: int argc;
349: char **argv;
350: {
351: char buf[50];
352: int args[3];
353: args[0] = atoi (argv[2]);
354: args[1] = atoi (argv[3]);
355: args[2] = atoi (argv[4]);
356: tparam1 (argv[1], buf, "LEFT", "UP", args);
357: printf ("%s\n", buf);
358: return 0;
359: }
360:
361: #endif /* DEBUG */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.