1 /*******************************************************************************
2  * Copyright (c) 2013-2021, Andrés Martinelli <andmarti@gmail.com>             *
3  * All rights reserved.                                                        *
4  *                                                                             *
5  * This file is a part of SC-IM                                                *
6  *                                                                             *
7  * SC-IM is a spreadsheet program that is based on SC. The original authors    *
8  * of SC are James Gosling and Mark Weiser, and mods were later added by       *
9  * Chuck Martin.                                                               *
10  *                                                                             *
11  * Redistribution and use in source and binary forms, with or without          *
12  * modification, are permitted provided that the following conditions are met: *
13  * 1. Redistributions of source code must retain the above copyright           *
14  *    notice, this list of conditions and the following disclaimer.            *
15  * 2. Redistributions in binary form must reproduce the above copyright        *
16  *    notice, this list of conditions and the following disclaimer in the      *
17  *    documentation and/or other materials provided with the distribution.     *
18  * 3. All advertising materials mentioning features or use of this software    *
19  *    must display the following acknowledgement:                              *
20  *    This product includes software developed by Andrés Martinelli            *
21  *    <andmarti@gmail.com>.                                                    *
22  * 4. Neither the name of the Andrés Martinelli nor the                        *
23  *   names of other contributors may be used to endorse or promote products    *
24  *   derived from this software without specific prior written permission.     *
25  *                                                                             *
26  * THIS SOFTWARE IS PROVIDED BY ANDRES MARTINELLI ''AS IS'' AND ANY            *
27  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED   *
28  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE      *
29  * DISCLAIMED. IN NO EVENT SHALL ANDRES MARTINELLI BE LIABLE FOR ANY           *
30  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES  *
31  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;*
32  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND *
33  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT  *
34  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE       *
35  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.           *
36  *******************************************************************************/
37 
38 /**
39  * \file sc.h
40  * \author Andrés Martinelli <andmarti@gmail.com>
41  * \date 2017-07-18
42  * \brief Header file for sc.c
43  */
44 
45 #ifndef SC_H_
46 #define SC_H_
47 
48 #include <stdio.h>
49 #include <memory.h>
50 
51 //#define ATBL(tbl, row, col)    (*(tbl + row) + (col))
52 extern struct ent ** ATBL(struct ent ***, int, int );
53 
54 #define MINROWS      100     /* minimum size at startup */
55 
56 /* MAX rows size of sheet. Default 65536.   */
57 /* Can be changed up to 1048576 in Makefile */
58 #ifndef MAXROWS
59 #define MAXROWS    65536
60 #endif
61 
62 #define MINCOLS       30
63 #define ABSMAXCOLS   702     /* MAX cols. (ZZ in base 26) */
64 
65 #define CRROWS         1
66 #define CRCOLS         2
67 
68 /* formats for engformat() */
69 #define REFMTFIX       0
70 #define REFMTFLT       1
71 #define REFMTENG       2
72 #define REFMTDATE      3
73 #define REFMTLDATE     4
74 #define DEFWIDTH      10     /* Default column width and precision */
75 #define DEFPREC        2
76 #define DEFREFMT      REFMTFIX /* Make default format fixed point  THA 10/14/90 */
77 #define FKEYS         24     /* Number of function keys available */
78 
79 #define COLFORMATS    10     /* Number of custom column formats */
80 #define FBUFLEN     1024     /* buffer size for a single field */
81 #define PATHLEN     1024     /* maximum path length */
82 
83 #define MAXCMD       160     /* for ! command and commands that use the pager */
84 #define STDERRBUF   8192     /* stderr buffer size */
85 
86 #ifndef DFLT_PAGER
87 #define    DFLT_PAGER "more" /* more is probably more widespread than less */
88 #endif                       /* DFLT_PAGER */
89 
90 #ifndef DFLT_EDITOR
91 #define    DFLT_EDITOR "vim"
92 #endif
93 
94 //#ifndef A_CHARTEXT         /* Should be defined in curses.h */
95 // #define A_CHARTEXT 0xff
96 //#endif
97 
98 #ifndef FALSE
99     # define    FALSE   0
100     # define    TRUE    1
101 #endif
102 
103 /*
104  * Some not too obvious things about the flags:
105  *    is_valid means there is a valid number in v.
106  *    is_locked means that the cell cannot be edited.
107  *    is_label set means it points to a valid constant string.
108  *    is_strexpr set means expr yields a string expression.
109  *    If is_strexpr is not set, and expr points to an expression tree, the
110  *        expression yields a numeric expression.
111  *    So, either v or label can be set to a constant.
112  *        Either (but not both at the same time) can be set from an expression.
113  */
114 
115 #define VALID_CELL(p, r, c) ((p = *ATBL(tbl, r, c)) && ((p->flags & is_valid) || p->label))
116 
117 // TODO Properly document these structs using doxygen tags. Possibly
118 // not the same as functions. What is the standard way?
119 
120 /* info for each cell, only alloc'd when something is stored in a cell */
121 struct ent {
122     double v;             /* v && label are set in EvalAll() */
123     char * label;
124     struct enode * expr;  /* cell's contents */
125     short flags;
126     int row, col;
127     struct ent * next;    // used for yanklist, freeents list, undo..
128     char * format;        /* printf format for this cell */
129     char cellerror;       /* error in a cell? */
130     struct ucolor * ucolor;
131     struct trigger * trigger;
132     int pad;              // padding between other cells
133 };
134 
135 #define FIX_ROW 1
136 #define FIX_COL 2
137 
138 /*
139  * ent_ptr holds the row/col # and address type of a cell
140  *
141  * vf is the type of cell address, 0 non-fixed, or bitwise OR of FIX_ROW or
142  *    FIX_COL
143  * vp : we just use vp->row or vp->col, vp may be a new cell just for holding
144  *    row/col (say in gram.y) or a pointer to an existing cell
145  */
146 struct ent_ptr {
147     int vf;
148     struct ent * vp;
149     struct enode * expr;  /* for getent */
150 };
151 
152 // stores a range (left, right)
153 struct range {
154     struct ent_ptr r_left, r_right;
155     char * r_name;
156     struct range * r_next, * r_prev;
157     int r_is_range;
158 };
159 
160 // holds the beginning/ending cells of a range
161 struct range_s {
162     struct ent_ptr left, right;
163 };
164 
165 /* stores type of operation this cell will perform */
166 struct enode {
167     int op;
168     union {
169 
170     struct {        /* other cells use to eval() / seval() */
171         struct enode * left, * right;
172         char *s;    /* previous value of @ext function in case */
173     } o;            /* external functions are turned off */
174 
175     int gram_match; /* some compilers (hp9000ipc) need this */
176     double k;       /* constant # */
177     char * s;       /* string part of a cell */
178 
179     struct range_s r;    /* op is on a range */
180     struct ent_ptr v;    /* ref. another cell on which this enode depends */
181     } e;
182 };
183 
184 struct impexfilt {
185     char ext[PATHLEN];
186     char plugin[PATHLEN];
187     char type;
188     struct impexfilt * next;
189 };
190 
191 /* Use this structure to save the last 'g' command */
192 struct go_save {
193     int g_type;
194     double g_n;
195     char * g_s;
196     int g_row;
197     int g_col;
198     int g_lastrow;
199     int g_lastcol;
200     int strow;
201     int stcol;
202     int stflag;
203     int errsearch;
204 };
205 
206 /* op values */
207 #define O_VAR       'v'
208 #define O_CONST     'k'
209 #define O_ECONST    'E'      /* constant cell w/ an error */
210 #define O_SCONST    '$'
211 #define REDUCE       0200    /* Or'ed into OP if operand is a range */
212 #define OP_BASE      256
213 #define ACOS        (OP_BASE + 0)
214 #define ASIN        (OP_BASE + 1)
215 #define ATAN        (OP_BASE + 2)
216 #define CEIL        (OP_BASE + 3)
217 #define COS         (OP_BASE + 4)
218 #define EXP         (OP_BASE + 5)
219 #define FABS        (OP_BASE + 6)
220 #define FLOOR       (OP_BASE + 7)
221 #define HYPOT       (OP_BASE + 8)
222 #define LOG         (OP_BASE + 9)
223 #define LOG10       (OP_BASE + 10)
224 #define POW         (OP_BASE + 11)
225 #define SIN         (OP_BASE + 12)
226 #define SQRT        (OP_BASE + 13)
227 #define TAN         (OP_BASE + 14)
228 #define DTR         (OP_BASE + 15)
229 #define RTD         (OP_BASE + 16)
230 #define SUM         (OP_BASE + 17)
231 #define PROD        (OP_BASE + 18)
232 #define AVG         (OP_BASE + 19)
233 #define COUNT       (OP_BASE + 20)
234 #define STDDEV      (OP_BASE + 21)
235 #define MAX         (OP_BASE + 22)
236 #define MIN         (OP_BASE + 23)
237 #define RND         (OP_BASE + 24)
238 #define HOUR        (OP_BASE + 25)
239 #define MINUTE      (OP_BASE + 26)
240 #define SECOND      (OP_BASE + 27)
241 #define MONTH       (OP_BASE + 28)
242 #define DAY         (OP_BASE + 29)
243 #define YEAR        (OP_BASE + 30)
244 #define NOW         (OP_BASE + 31)
245 #define DATE        (OP_BASE + 32)
246 #define FMT         (OP_BASE + 33)
247 #define SUBSTR      (OP_BASE + 34)
248 #define STON        (OP_BASE + 35)
249 #define EQS         (OP_BASE + 36)
250 #define EXT         (OP_BASE + 37)
251 #define ELIST       (OP_BASE + 38)    /* List of expressions */
252 #define LMAX        (OP_BASE + 39)
253 #define LMIN        (OP_BASE + 40)
254 #define NVAL        (OP_BASE + 41)
255 #define SVAL        (OP_BASE + 42)
256 #define PV          (OP_BASE + 43)
257 #define FV          (OP_BASE + 44)
258 #define PMT         (OP_BASE + 45)
259 #define STINDEX     (OP_BASE + 46)
260 #define LOOKUP      (OP_BASE + 47)
261 #define ATAN2       (OP_BASE + 48)
262 #define INDEX       (OP_BASE + 49)
263 #define DTS         (OP_BASE + 50)
264 #define TTS         (OP_BASE + 51)
265 #define ABS         (OP_BASE + 52)
266 #define HLOOKUP     (OP_BASE + 53)
267 #define VLOOKUP     (OP_BASE + 54)
268 #define ROUND       (OP_BASE + 55)
269 #define IF          (OP_BASE + 56)
270 #define FILENAME    (OP_BASE + 57)
271 #define MYROW       (OP_BASE + 58)
272 #define MYCOL       (OP_BASE + 59)
273 #define LASTROW     (OP_BASE + 60)
274 #define LASTCOL     (OP_BASE + 61)
275 #define COLTOA      (OP_BASE + 62)
276 #define UPPER       (OP_BASE + 63)
277 #define LOWER       (OP_BASE + 64)
278 #define CAPITAL     (OP_BASE + 65)
279 #define NUMITER     (OP_BASE + 66)
280 #define ERR_        (OP_BASE + 67)
281 #define PI_         (OP_BASE + 68)
282 #define REF_        (OP_BASE + 69)
283 #define SLEN        (OP_BASE + 77)
284 #define ASCII       (OP_BASE + 78)
285 #define CHR         (OP_BASE + 79)
286 #define SET8BIT     (OP_BASE + 80)
287 #define REPLACE     (OP_BASE + 81)
288 #define FROW        (OP_BASE + 82)
289 #define FCOL        (OP_BASE + 83)
290 #define LUA         (OP_BASE + 84)
291 #define FACT        (OP_BASE + 85)
292 #define GETENT      (OP_BASE + 86)
293 #define EVALUATE    (OP_BASE + 87)
294 #define SEVALUATE   (OP_BASE + 88)
295 
296 /* flag values */
297 #define is_valid      0001
298 #define is_changed    0002
299 #define is_strexpr    0004
300 #define is_leftflush  0010
301 #define is_deleted    0020
302 #define is_locked     0040
303 #define is_label      0100
304 #define iscleared     0200
305 #define may_sync      0400
306 /* cell error (1st generation (ERROR) or 2nd+ (INVALID)) */
307 #define CELLOK        0
308 #define CELLERROR     1
309 #define CELLINVALID   2
310 #define CELLREF       3
311 /* calculation order */
312 #define BYCOLS        1
313 #define BYROWS        2
314 /* tblprint style output for: */
315 #define TBL           1       /* 'tbl' */
316 #define LATEX         2       /* 'LaTeX' */
317 #define TEX           3       /* 'TeX' */
318 #define SLATEX        4       /* 'SLaTeX' (Scandinavian LaTeX) */
319 #define FRAME         5       /* tblprint style output for FrameMaker */
320 /* Types for etype() */
321 #define NUM           1
322 #define STR           2
323 #define GROWAMT       30      /* default minimum amount to grow */
324 #define GROWNEW       1       /**< first time table */
325 #define GROWROW       2       /* add rows */
326 #define GROWCOL       3       /* add columns */
327 #define GROWBOTH      4       /* grow both */
328 
329 extern int currow, curcol;
330 extern int maxrow, maxcol;
331 extern struct ent *** tbl;     // data table ref. in vmtbl.c and ATBL()
332 extern char curfile[];
333 extern int arg;
334 extern int lastrow, lastcol;
335 extern int gmyrow, gmycol;    // globals used for @myrow, @mycol cmds
336 extern int rescol;            // columns reserved for row numbers
337 extern int maxrows, maxcols;  // # cells currently allocated
338 extern int rowsinrange;       // Number of rows in target range of a goto
339 extern int colsinrange;       // Number of cols in target range of a goto
340 extern int * fwidth;
341 extern int * precision;
342 extern int * realfmt;
343 extern char * colformat[10];
344 extern unsigned char * col_hidden;
345 extern unsigned char * row_hidden;
346 extern unsigned char * row_format;
347 extern unsigned char * row_frozen;
348 extern unsigned char * col_frozen;
349 extern char line[FBUFLEN];
350 extern int linelim;
351 extern int changed;
352 extern int dbidx;
353 extern int qbuf;              // buffer no. specified by `"' command
354 extern int showsc, showsr;    // starting cell of highlighted range
355 extern int cellassign;
356 extern int macrofd;
357 extern int cslop;
358 extern int usecurses;
359 extern int brokenpipe;        // Set to true if SIGPIPE is received
360 extern int modflg;
361 extern char * mdir;
362 extern char * autorun;
363 extern int skipautorun;
364 extern char * fkey[FKEYS];
365 extern char * scext;
366 extern int repct;
367 extern int calc_order;
368 extern double prescale;
369 extern int propagation;
370 extern int optimize;
371 extern int color;
372 extern int numeric;
373 extern int colorneg;
374 extern int colorerr;
375 extern int rndtoeven;
376 extern int tbl_style;
377 extern int loading;
378 
379 extern struct enode * copye(struct enode *e, int Rdelta, int Cdelta, int r1, int c1, int r2, int c2, int transpose);
380 extern char dpoint;   // country-dependent decimal point from locale
381 extern char thsep;    // country-dependent thousands separator from locale
382 extern char * coltoa(int col);
383 extern char * findplugin(char * ext, char type);
384 extern char * findhome(char * path);
385 extern char * r_name(int r1, int c1, int r2, int c2);
386 extern char * scxmalloc(unsigned n);
387 extern char * scxrealloc(char * ptr, unsigned n);
388 extern char * seval(struct ent * ent, struct enode * se);
389 extern char * v_name(int row, int col);
390 extern double eval(struct ent * ent, struct enode * e);
391 extern struct enode * new(int op, struct enode * a1, struct enode * a2);
392 extern struct enode * new_const(int op, double a1);
393 extern struct enode * new_range(int op, struct range_s a1);
394 extern struct enode * new_str(char * s);
395 extern struct enode * new_var(int op, struct ent_ptr a1);
396 extern struct ent * lookat(int row, int col);
397 extern void EvalAll();
398 extern void checkbounds(int * rowp, int * colp);
399 extern void clearent(struct ent * v);
400 extern void closefile(FILE * f, int pid, int rfd);
401 extern void colshow_op();
402 extern struct colorpair *cpairs[8];
403 extern void editexp(int row, int col);
404 extern void efree(struct enode * e);
405 extern void label(struct ent * v, char * s, int flushdir);
406 
407 extern double eval_result;
408 extern char * seval_result;
409 #endif // SC_H_
410