home *** CD-ROM | disk | FTP | other *** search
- /* Copyright (C) 1990 Free Software Foundation, Inc.
-
- This file is part of Oleo, the GNU Spreadsheet.
-
- Oleo is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 1, or (at your option)
- any later version.
-
- Oleo is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with Oleo; see the file COPYING. If not, write to
- the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
-
- #include <ctype.h>
- #include <errno.h>
- #include <fcntl.h>
- #include <stdio.h>
- #include <signal.h>
-
- #ifdef I_IOCTL
- #include <sys/ioctl.h>
- #endif
-
- #include "funcdef.h"
-
- #define obstack_chunk_alloc ck_malloc
- #define obstack_chunk_free free
- #include "obstack.h"
-
- #ifdef __TURBOC__
- #define RCFILE "oleo.rc"
- #else
- #define RCFILE ".oleorc"
- #endif
-
- #include "sysdef.h"
-
- #include "global.h"
- #include "cell.h"
- #include "kbd.h"
-
- #define CTRL(X) ((X)&037)
-
- #define LINE_MIN 28
-
- #ifdef __TURBOC__
- #define TIMER_MULT 10000
- #else
- #if defined(NO_UALARM) && !defined(SETITIMER)
- #define TIMER_MULT 1/10
- #else
- #define TIMER_MULT 100000
- #endif
- #endif
-
- /* Structures for this file */
-
- /* for func_flags */
- #define NONTOP 0x1
- #define TOPLN 0x2
-
- #define ALL 0x3
-
-
- #define WTH_CHR 0x4
- #define BRK 0x8
- #define NC 0x10
-
- struct line {
- int alloc;
- char *buf;
- };
-
- struct macro {
- struct macro *mac_prev;
- unsigned char *mac_exe;
- int mac_flags;
- CELLREF mac_row, mac_col;
- struct rng mac_rng;
- };
-
- /* External spreadsheet functions */
-
- /* utils.c */
- extern char *char_to_string EXT1(char);
- extern int string_to_char EXT1(char **);
- extern FILE *xopen_with_backup EXT2(const char *,const char *);
- extern int xclose EXT1(FILE *);
- extern char *err_msg EXT0();
- extern char *mk_sprintf EXT1N(char *);
-
- extern void init_mem EXT0();
- extern void init_eval EXT0();
- extern void init_refs EXT0();
- extern void init_cells EXT0();
-
- extern void panic_read_file EXT2(FILE *,int);
- extern void panic_write_file EXT2(FILE *,struct rng *);
- extern int panic_set_options EXT2(int, char *);
- extern void panic_show_options EXT0();
-
- #ifdef USE_DLD
- /* If we're using dynamic linking, we get the names of the
- functions to call by prepending the basename of save_name onto
- _read_file
- _write_file
- _set_options
- _show_options
- so, if the file is sylk.o , the functions are named
- sylk_read_file
- sylk_write_file
- sylk_set_options
- sylk_show_options
- */
- char *io_name;
-
- #else
-
- extern void sylk_read_file EXT2(FILE *,int);
- extern void sylk_write_file EXT2(FILE *,struct rng *);
- extern int sylk_set_options EXT2(int, char *);
- extern void sylk_show_options EXT0();
-
- extern void sc_read_file EXT2(FILE *,int);
- extern void sc_write_file EXT2(FILE *,struct rng *);
- extern int sc_set_options EXT2(int, char *);
- extern void sc_show_options EXT0();
-
- extern void list_read_file EXT2(FILE *,int);
- extern void list_write_file EXT2(FILE *,struct rng *);
- extern int list_set_options EXT2(int, char *);
- extern void list_show_options EXT0();
-
- /* extern char sl_sep; */
-
- #endif
-
- /* regions.c */
- extern void set_rng EXT5(struct rng *, CELLREF, CELLREF, CELLREF, CELLREF);
- extern void lock_region EXT2(struct rng *, int);
- extern void format_region EXT3(struct rng *, int, int);
- extern unsigned short print_width;
-
- /* ref.c */
- extern int eval_next_cell EXT0();
- extern struct var *find_var EXT2(char *, int);
- extern timer_active;
-
- /* io_utils.c */
- extern void get_usr_stats EXT2(int, char **);
- extern void set_usr_stats EXT2(int, char **);
-
- /* io_disp.c */
- extern void redisp EXT0();
- extern void open_display EXT1(int);
- extern void clear_top_before EXT0();
- extern void clear_top_after EXT0();
- extern void close_display();
- extern void disp_scrn EXT0();
- extern int get_chr_prompt EXT1(char *);
- extern void recenter_cur_win EXT0();
- extern void recenter_all_win EXT0();
- extern void cur_status EXT0();
- extern int move_cell_cursor EXT2(CELLREF, CELLREF);
- extern int get_inp_line EXT2(char *, struct line *);
-
- /* utils.c */
- extern char *myname;
- extern int __make_backups;
- extern int __backup_by_copying;
-
-
- /* Routines for manipulating 'struct line's */
- void set_line EXT2(struct line *, char *);
-
- /* Terminal I/O functions */
- int get_chr EXT0();
-
- static unsigned char real_get_chr EXT0();
-
- /* Routines for manipulating key bindings */
- static void do_bind_key EXT4(struct keymap *, int, unsigned char, unsigned char);
- static void desc_map EXT1(struct keymap *);
-
- /* File I/O functions */
- static FILE *open_file EXT3(char *, struct line *, char *);
- static void close_file EXT2(struct line *, FILE *);
-
- /* Routines for putting info into 'struct rng's */
- static int get_two_ranges EXT4(char *, struct rng *, struct rng *, struct line *);
- static FILE * get_range_and_file EXT3(char *, struct rng *, struct line *);
- static int get_a_range EXT3(char *,struct rng *,struct line *);
- static int get_abs_rng EXT2(char **, struct rng *);
-
- static void sprint_line EXT2N(struct line *, char *);
-
- /* Routines for converting text<-->cell_format */
- static int str_to_fmt EXT1(char *);
-
- /* Routines for converting text<-->cell_jst */
- static int chr_to_jst EXT1(int);
-
- /* Routines for implementing user commands */
- int global_cmd EXT1(int);
-
- void set_options EXT1(char *);
-
- /* Backends for other functions */
- static int do_set_option EXT1(char *);
-
-
- /* Spreadsheet (global) functions declared in this file */
-
-
- int main EXT2(int, char **);
-
- void map_chr EXT1(int);
-
- extern void clear_spreadsheet EXT0();
-
- void pr_cell EXT3(CELLREF, CELLREF, CELL *);
-
- char *cell_name EXT2(CELLREF, CELLREF);
- char *range_name EXT1(struct rng *);
-
- char *fmt_to_str EXT1(int);
- char *jst_to_str EXT1(int);
-
- #ifdef A0_REFS
- char *col_to_str EXT1(CELLREF);
- #endif
-
- const int colmagic[] = {
- 0, 0, 1,-1, 1,-1, 1,-1, 0};
- const int rowmagic[] = {
- -1, 1, 0, 0,-1,-1, 1, 1, 0};
-
- char * ename[] = {
- "#WHAT?",
- "#ERROR", "#BAD_INPUT", "#NON_NUMBER", "#NON_STRING",
- "#NON_BOOL", "#NON_RANGE", "#OUT_OF_RANGE","#NO_VALUES",
- "#DIV_BY_ZERO", "#BAD_NAME", "#NOT_AVAIL", "#PARSE_ERROR",
- "#NEED_OPEN", "#NEED_CLOSE", "#NEED_QUOTE", "#UNK_CHAR",
- "#UNK_FUNC",
- 0
- };
-
- const char tname[] = "#TRUE";
- const char fname[] = "#FALSE";
-
-
- int cur_chr;
- struct cmd_func *cur_cmd;
- unsigned char cur_vector;
-
- /* User settable options */
- int bkgrnd_recalc = 1;
- int auto_recalc = 1;
- /* Original value is 10 seconds/tick */
- unsigned signal_ticks = 10 * TIMER_MULT;
-
- void (*read_file) EXT2(FILE *,int) = panic_read_file;
- void (*write_file) EXT2(FILE *,struct rng *) = panic_write_file;
- int (*set_file_opts) EXT2(int, char *) = panic_set_options;
- void (*show_file_opts) EXT0() = panic_show_options;
-
- int n_bound_macros;
- struct rng *bound_macros;
- int bound_macro_vec;
-
- char *macro_func_arg = 0;
-
- /* This variable is non-zero if the spreadsheet has been changed in any way */
- int modified = 0;
-
- CELLREF setrow,
- setcol;
-
- CELLREF curow = MIN_ROW,
- cucol = MIN_COL;
-
- CELLREF mkrow = NON_ROW,
- mkcol = NON_COL;
-
- struct rng mkrng;
-
- /* CELLREF srl,srh,scl,sch; */
-
- unsigned int how_many = 1;
-
- static struct macro *rmac = 0;
- static struct obstack macro_stack;
-
- static unsigned char *making_macro;
- static unsigned char *making_macro_start;
- static unsigned int making_macro_size;
-
- /* If 2, clear the top line before reading a character */
- /* if 1, clear it after reading a char */
- int topclear = 0;
-
- struct line val_line;
- struct line fmt_line;
- struct line wid_line;
-
- /* Lines 'a' through 'z' */
- struct line in_line[26];
-
- unsigned short default_width=8;
- int default_jst = JST_LFT;
- int default_fmt = FMT_GEN;
- int default_lock = LCK_UNL;
-
- #ifndef __TURBOC__
- char buf[BUFSIZ];
- int term_flag;
-
- void got_sigio EXT1(int);
- #endif
- static void got_sigint EXT1(int);
-
- extern char print_buf[];
-
-
- struct keymap **the_maps;
- char **map_names;
- int num_maps;
-
- struct cmd_func **the_funcs;
- int num_funcs;
-
- /* Keymap stuff: This is the 'main' keymap */
-
- #define GO_UP_CMD 1 /* We want these-all to be low */
- #define GO_DN_CMD 2 /* numbers so that rowmagic and */
- #define GO_RT_CMD 3 /* colmagic can be small arrays */
- #define GO_LF_CMD 4 /* Also note that GO, SCR, and */
- #define GO_UPRT_CMD 5 /* MAGIC mumble must all be in */
- #define GO_UPLF_CMD 6 /* the same order, and they */
- #define GO_DNRT_CMD 7 /* must all agree with rowmagic */
- #define GO_DNLF_CMD 8 /* and colmagic */
-
- #define SCR_UP_CMD 9
- #define SCR_DN_CMD 10
- #define SCR_RT_CMD 11
- #define SCR_LF_CMD 12
- #define SCR_UPRT_CMD 13
- #define SCR_UPLF_CMD 14
- #define SCR_DNRT_CMD 15
- #define SCR_DNLF_CMD 16
-
- #define SCAN_UP_CMD 17
- #define SCAN_DN_CMD 18
- #define SCAN_RT_CMD 19
- #define SCAN_LF_CMD 20
-
- #define BREAK_CMD 21
- #define RECENTER_CMD 22
- #define SET_OPT_CMD 23
- #define SET_DEF_CMD 24
- #define QUIT_CMD 25
- #define REDRAW_CMD 26
- #define USR_FMT_CMD 27
-
- #define SET_VAR_CMD 28
- #define SHO_VAR_CMD 29
- #define SHO_ALL_VAR_CMD 30
-
- #define RECALC_CMD 31
- #define BIND_KEY_CMD 32
- #define DESC_KEY_CMD 33
- #define READ_KEY_CMD 34
- #define SAVE_KEY_CMD 35
-
- #define WRITE_ALL_CMD 36
- #define READ_ALL_CMD 37
- #define READ_MERGE_CMD 38
- #define KILL_ALL_CMD 39
-
- #define COPY_REG 40
- #define COPY_VAL_REG 41
- #define FORMAT_REG 42
- #define MOVE_REG 43
- #define PRINT_REG 44
- #define SORT_REG 45
- #define WRITE_REG 46
- #define KILL_REG 47
-
- #define START_MACRO 48
- #define EXECUTE_MACRO 49
- #define INTERACT_MACRO 50
-
- #define GOTO_CMD 51
- #define SET_MARK_CMD 52
- #define EDIT_CELL 53
- #define EDIT_VAL_CELL 54
- #define FORMAT_CELL 55
- #define KILL_CELL 56
- #define NEW_DEF_CELL 57
-
- #define DIGIT_0 58
- #define DIGIT_1 59
- #define DIGIT_2 60
- #define DIGIT_3 61
- #define DIGIT_4 62
- #define DIGIT_5 63
- #define DIGIT_6 64
- #define DIGIT_7 65
- #define DIGIT_8 66
- #define DIGIT_9 67
-
- #define NEW_CELL 68
-
- #define SHOW_OPT_CMD 69
-
- #define OPEN_WIN_CMD 70
- #define CLOSE_WIN_CMD 71
- #define GOTO_WIN_CMD 72
-
- #define END_MACRO 73
- #define MK_KEYMAP 74
-
- #ifdef TEST
- #define DEBUG_CMD 75
-
- #endif
-
- static struct key main_keys_1[] = {
- { 0, SET_MARK_CMD }, /* ^@ */
- { 0, UNBOUND },
- { 0, GO_LF_CMD },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 0, UNBOUND }, /* ^E */
- { 0, GO_RT_CMD },
- { 0, BREAK_CMD },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 0, UNBOUND }, /* ^J */
- { 0, UNBOUND },
- { 0, RECENTER_CMD },
- { 0, UNBOUND },
- { 0, GO_DN_CMD },
- { 0, UNBOUND }, /* ^O */
- { 0, GO_UP_CMD },
- { 0, UNBOUND },
- { 0, REDRAW_CMD },
- { 0, UNBOUND },
- { 0, UNBOUND }, /* ^T */
- { 0, UNBOUND },
- { 0, SHO_ALL_VAR_CMD },
- { 0, UNBOUND },
- { 0, KILL_ALL_CMD },
- { 0, UNBOUND }, /* ^Y */
- { 0, UNBOUND },
- { 255, META_MAP }, /* ^[ */
- { 0, UNBOUND }, /* ^\ */
- { 0, UNBOUND }, /* ^] */
- { 0, UNBOUND }, /* ^^ */
- { 0, UNBOUND }, /* ^_ */
- { 0, NEW_CELL }, /* space */
- { 0, RECALC_CMD }, /* ! */
- { 0, NEW_CELL }, /* " */
- { 0, NEW_CELL }, /* # */
- { 0, NEW_CELL }, /* $ */
- { 0, UNBOUND }, /* % */
- { 0, UNBOUND }, /* & */
- { 0, UNBOUND }, /* ' */
- { 0, NEW_CELL }, /* ( */
- { 0, UNBOUND }, /* ) */
- { 0, UNBOUND }, /* * */
- { 0, NEW_CELL }, /* + */
- { 0, UNBOUND }, /* , */
- { 0, NEW_CELL }, /* - */
- { 0, NEW_CELL }, /* . */
- { 0, UNBOUND }, /* / */
- { 0, NEW_CELL }, /* 0 */
- { 0, NEW_CELL }, /* 1 */
- { 0, NEW_CELL }, /* 2 */
- { 0, NEW_CELL }, /* 3 */
- { 0, NEW_CELL }, /* 4 */
- { 0, NEW_CELL }, /* 5 */
- { 0, NEW_CELL }, /* 6 */
- { 0, NEW_CELL }, /* 7 */
- { 0, NEW_CELL }, /* 8 */
- { 0, NEW_CELL }, /* 9 */
- { 0, BIND_KEY_CMD }, /* : */
- { 0, DESC_KEY_CMD }, /* ; */
- { 0, UNBOUND }, /* < */
- { 0, NEW_DEF_CELL }, /* = */
- { 0, UNBOUND }, /* > */
- { 0, UNBOUND }, /* ? */
- { 0, NEW_CELL }, /* @ */
- { 0, UNBOUND }, /* A */
- { 0, SCR_DNLF_CMD },
- { 0, COPY_VAL_REG },
- { 0, UNBOUND },
- { 0, EDIT_VAL_CELL },
- { 0, FORMAT_REG }, /* F */
- { 0, UNBOUND },
- { 0, SCR_LF_CMD },
- { 0, UNBOUND },
- { 0, SCR_DN_CMD },
- { 0, SCR_UP_CMD }, /* K */
- { 0, SCR_RT_CMD },
- { 0, UNBOUND },
- { 0, SCR_DNRT_CMD },
- { 0, SHOW_OPT_CMD },
- { 0, UNBOUND }, /* P */
- { 0, QUIT_CMD },
- { 0, READ_MERGE_CMD },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 0, SCR_UPRT_CMD }, /* U */
- { 0, SHO_VAR_CMD },
- { 0, WRITE_REG },
- { 0, KILL_REG },
- { 0, SCR_UPLF_CMD },
- { 0, UNBOUND }, /* Z */
- { 0, UNBOUND }, /* [ */
- { 0, UNBOUND }, /* \ */
- { 0, UNBOUND }, /* ] */
- { 0, UNBOUND }, /* ^ */
- { 0, UNBOUND }, /* _ */
- { 0, UNBOUND }, /* ` */
- { 0, UNBOUND }, /* a */
- { 0, GO_DNLF_CMD },
- { 0, COPY_REG },
- { 0, SET_DEF_CMD },
- { 0, EDIT_CELL },
- { 0, FORMAT_CELL }, /* f */
- { 0, GOTO_CMD },
- { 0, GO_LF_CMD },
- { 0, UNBOUND },
- { 0, GO_DN_CMD },
- { 0, GO_UP_CMD }, /* k */
- { 0, GO_RT_CMD },
- { 0, MOVE_REG },
- { 0, GO_DNRT_CMD },
- { 0, SET_OPT_CMD },
- { 0, PRINT_REG }, /* p */
- { 0, UNBOUND },
- { 0, READ_ALL_CMD },
- { 0, SORT_REG },
- { 0, UNBOUND },
- { 0, GO_UPRT_CMD }, /* u */
- { 0, SET_VAR_CMD },
- { 0, WRITE_ALL_CMD },
- { 0, KILL_CELL },
- { 0, GO_UPLF_CMD } /* y */
- };
- static struct key main_keys_2[] = {
- { 255, ANSI_MAP } /* CSI , 0x9b hopefully */
- };
-
- struct keymap main_map[] = {
- {&main_map[1], 0, 0, 1,
- '\0','y',
- &main_keys_1[0]},
-
- {0, 1, 0, 1,
- '\233','\233',
- &main_keys_2[0]}
- };
-
- /* The meta-map, for key sequences that start with escape */
- /* We declare these in reverse order so we won't have to forward-reference
- all the pointers. . . */
- static struct key meta_key_4[] = {
- { 0, USR_FMT_CMD },
- { 0, UNBOUND },
- { 0, OPEN_WIN_CMD },
- { 0, EXECUTE_MACRO },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 255, ANSI_MAP }
- };
-
- static struct key meta_key_3[] = {
- { 0, CLOSE_WIN_CMD },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 0, GOTO_WIN_CMD },
- { 0, SCAN_LF_CMD },
- { 0, UNBOUND },
- { 0, SCAN_DN_CMD },
- { 0, SCAN_UP_CMD },
- { 0, SCAN_RT_CMD },
- };
-
- static struct key meta_key_2[] = {
- { 0, DIGIT_0 },
- { 0, DIGIT_1 },
- { 0, DIGIT_2 },
- { 0, DIGIT_3 },
- { 0, DIGIT_4 },
- { 0, DIGIT_5 },
- { 0, DIGIT_6 },
- { 0, DIGIT_7 },
- { 0, DIGIT_8 },
- { 0, DIGIT_9 },
- { 0, UNBOUND },
- { 0, UNBOUND },
- { 0, READ_KEY_CMD },
- { 0, UNBOUND },
- { 0, SAVE_KEY_CMD }
- };
-
- static struct key meta_key_1[] = {
- { 0, START_MACRO },
- { 0, END_MACRO }
- };
-
- #ifdef TEST
- #define DBG_ADD 1
- static struct key meta_key_0 = { 0, DEBUG_CMD };
- #else
- #define DBG_ADD 0
- #endif
-
- struct keymap meta_map[] = {
- #ifdef TEST
- {
- &meta_map[DBG_ADD], 0, 0, 1,
- CTRL('d'),CTRL('d'),
- &meta_key_0
- },
- #endif
- {
- &meta_map[1+DBG_ADD], 0, 0, 1,
- '(',')',
- &meta_key_1[0]
- },{
- &meta_map[2+DBG_ADD], 0, 0, 0,
- '0','>',
- &meta_key_2[0]
- },{
- &meta_map[3+DBG_ADD], 0, 0, 0,
- 'C', 'L',
- &meta_key_3[0]
- },{
- &meta_map[4+DBG_ADD], 0, 0, 0,
- 'U','[',
- &meta_key_4[0]
- },{
- &meta_map[5+DBG_ADD], 0, 0, 0,
- 'c', 'l',
- &meta_key_3[0],
- },{
- 0, 1, 0, 0,
- 'u', 'x',
- &meta_key_4[0]
- }
- };
-
- /* For keyboards that return ^[ [ {A B C D} for the arrow keys */
- static struct key ansi_key[] = {
- { 0, GO_UP_CMD },
- { 0, GO_DN_CMD },
- { 0, GO_RT_CMD },
- { 0, GO_LF_CMD }
- };
-
- struct keymap ansi_map = {
- 0, 1, 0, 1,
- 'A', 'D',
- &ansi_key[0]
- };
- /* FOr dealing with meta-digit commands */
- static struct keymap digit_map = {
- &main_map[0], 1, 0, 0,
- '0','9',
- &meta_key_2[0]
- };
-
- /* The user commands that are defined in this file. . . */
- extern void scroll_cell_cursor EXT1(int);
- extern void copy_region();
- extern void copy_values_region();
- extern void set_format();
- extern void move_region();
- extern void delete_region();
- extern void format_area();
- extern void open_window();
- extern void close_window();
- extern void goto_window();
- extern void print_region EXT2(struct rng *, char *);
-
- static void do_debug EXT1(char *);
- static void end_macro EXT0();
- /* static void do_ansi_cmd EXT0(); */
- static void do_break_cmd EXT0();
- static void set_default EXT0();
- static void quit_cmd EXT0();
- static void set_usr_fmt EXT1(char *);
- static void set_var EXT1(char *);
- static void show_var EXT1(char *);
- static void show_all_var EXT0();
- static void recalc_cmd EXT0();
- static void bind_key_cmd EXT1(char *);
- static void desc_key_cmd EXT0();
- static void read_cmds_cmd EXT1(FILE *);
- static void write_keys_cmd EXT1(FILE *);
- static void write_cmd EXT1(FILE *);
- static void read_cmd EXT1(FILE *);
- static void read_merge_cmd EXT1(FILE *);
- static void kill_all_cmd EXT0();
- static void sort_region_cmd EXT1(char *);
- static void write_reg_cmd EXT2(FILE *, struct rng *);
- static void start_macro EXT0();
- static void execute_cmd EXT1(char *);
- static void interact_macro_cmd EXT0();
- static void goto_region EXT1(struct rng *);
- static void mark_cell_cmd EXT0();
- static void do_input_cmd EXT2(int, int);
- static void format_cell_cmd EXT0();
- static void kill_cell_cmd EXT0();
- static void digit_cmd EXT1(int);
- static void show_options EXT0();
- static void bound_macro EXT1(int);
- static void make_keymap EXT1(char *);
- static void scan_cell_cursor EXT1(int);
- static void shift_cell_cursor EXT1(int);
-
- /* For lines that take text input, the second letter (eg 'ta' or 'fdr')
- specifies which struct line to use to contain the text generated for that
- command. That way, the command will have the appropriate defaults, etc.
- Currently 'a' through 'n' are used (?).
- a set options
- b set/show variables
- c read/write keymap
- d read/write file
- e read-merge write-region
- f copy region/copy values region
- g format-region
- h move-region
- i print-region
- j sort-region
- k delete-region
- l execute-command
- m goto-cell
- n open-window
- o close-window
- p debug
- q bind-key
- r set-user-format
- s create-keymap
- */
-
- static struct cmd_func cmd_funcs[] = {
- { "unbound", 0, ALL, 0 },
-
- { "go-up", "n0", ALL, shift_cell_cursor },
- { "go-down", "n1", ALL, shift_cell_cursor },
- { "go-right", "n2", ALL, shift_cell_cursor },
- { "go-left", "n3", ALL, shift_cell_cursor },
- { "go-upright", "n4", ALL, shift_cell_cursor },
- { "go-upleft", "n5", ALL, shift_cell_cursor },
- { "go-downright", "n6", ALL, shift_cell_cursor },
- { "go-downleft", "n7", ALL, shift_cell_cursor },
-
- { "scroll-up", "n0", ALL, scroll_cell_cursor },
- { "scroll-down", "n1", ALL, scroll_cell_cursor },
- { "scroll-right", "n2", ALL, scroll_cell_cursor },
- { "scroll-left", "n3", ALL, scroll_cell_cursor },
- { "scroll-upright", "n4", ALL, scroll_cell_cursor },
- { "scroll-upleft", "n5", ALL, scroll_cell_cursor },
- { "scroll-downright", "n6", ALL, scroll_cell_cursor },
- { "scroll-downleft", "n7", ALL, scroll_cell_cursor },
-
- { "scan-up", "n0", ALL, scan_cell_cursor },
- { "scan-down", "n1", ALL, scan_cell_cursor },
- { "scan-right", "n2", ALL, scan_cell_cursor },
- { "scan-left", "n3", ALL, scan_cell_cursor },
-
- { "break", 0, ALL|BRK,do_break_cmd },
- { "recenter-window", 0, ALL, recenter_cur_win },
- { "set-option", "ta", ALL, set_options },
- { "set-defaults", "T", ALL, set_default },
- { "quit", "C", ALL, quit_cmd },
- { "redraw-screen", 0, ALL, disp_scrn },
- { "set-user-format", "trT", ALL, set_usr_fmt },
-
- /* If you change the line used by {set,show}-variable, you must change
- {set,show}_var to use the correct line, else bad things will happen */
- { "set-variable", "tb", ALL, set_var },
- { "show-variable", "tb", ALL, show_var },
- { "show-all-variables", 0, ALL, show_all_var },
-
- { "recalculate", 0, ALL, recalc_cmd },
- { "bind-key", "tqT", ALL, bind_key_cmd },
- { "describe-key", "T", ALL, desc_key_cmd },
- { "read-commands", "fcr", ALL, read_cmds_cmd },
- { "write-keys", "fcw", ALL, write_keys_cmd },
-
- /* If you change the line used by {read,write}-file, you must change
- main() to use the correct line, else chaos will erupt */
- { "write-file", "fdw", ALL, write_cmd },
- { "read-file", "Cfdr", ALL, read_cmd },
- { "read-merge", "fer", ALL, read_merge_cmd },
- { "clear-spreadsheet", "C", ALL, kill_all_cmd },
-
- { "copy-region", "Rf", ALL, copy_region },
- { "copy-values-in_region","Rf", ALL, copy_values_region },
- { "format-region", "rg", ALL, format_area },
- { "move-region", "Rh", ALL, move_region },
- { "print-region", "Fi", ALL, print_region },
- { "sort-region", "tj", ALL, sort_region_cmd },
- { "write-region-to-file", "Fe", ALL, write_reg_cmd },
- { "delete-region", "rk", ALL, delete_region },
-
- { "start-entering-macro", 0, ALL, start_macro },
- { "execute-command", "tl", ALL, execute_cmd },
- { "macro-interactive-here",0, ALL, interact_macro_cmd },
-
- /* If you change which line goto-cell uses, you *must* modify goto_region() */
- { "goto-cell", "rm", ALL, goto_region },
- { "mark-cell", 0, ALL, mark_cell_cmd },
- { "edit-cell", "T0", ALL|WTH_CHR,do_input_cmd },
- { "edit-value-cell", "T1", ALL|WTH_CHR,do_input_cmd },
- { "format-cell", "T", ALL, format_cell_cmd },
- { "delete-cell", 0, ALL, kill_cell_cmd },
- { "edit-cell-with-default","T3", ALL|WTH_CHR,do_input_cmd },
-
- { "digit-0", "N", ALL|NC, digit_cmd },
- { "digit-1", "N", ALL|NC, digit_cmd },
- { "digit-2", "N", ALL|NC, digit_cmd },
- { "digit-3", "N", ALL|NC, digit_cmd },
- { "digit-4", "N", ALL|NC, digit_cmd },
- { "digit-5", "N", ALL|NC, digit_cmd },
- { "digit-6", "N", ALL|NC, digit_cmd },
- { "digit-7", "N", ALL|NC, digit_cmd },
- { "digit-8", "N", ALL|NC, digit_cmd },
- { "digit-9", "N", ALL|NC, digit_cmd },
-
- { "enter-text-in-cell", "T2", WTH_CHR|ALL,do_input_cmd },
-
- { "show-options", 0, ALL, show_options },
-
- { "open-window", "tn", ALL, open_window },
- { "close-window", "to", ALL, close_window },
- { "goto-window", "to", ALL, goto_window },
-
- { "stop-entering-macro", 0, ALL, end_macro },
-
- { "create-keymap", "ts", ALL, make_keymap },
-
- #ifdef TEST
- { "debug", "tp", ALL, do_debug },
- #endif
-
- { "bound-menu", 0, WTH_CHR|ALL,0 },
- { 0, 0, 0, 0 }
-
- };
-
-
-
- #ifdef __TURBOC__
- extern void deal_alarm EXT0();
-
- static unsigned char
- real_get_chr FUN0()
- {
- unsigned char ch;
-
- if(auto_recalc) {
- current_cycle++;
- if(!bkgrnd_recalc) {
- while(eval_next_cell())
- ;
- } else {
- if(timer_active) {
-
- static int ttick;
- int ev = 1;
-
- for(;kbhit()==0;) {
- if(ev) {
- ev=eval_next_cell();
- if(!ev)
- redisp();
- }
- if(ttick++>=signal_ticks) {
- deal_alarm();
- ttick=0;
- ev=1;
- }
- }
- }
-
- while(kbhit()==0 && eval_next_cell())
- ;
- }
- }
- redisp();
- ch=getch();
- if(making_macro) {
- if(ch==0)
- *making_macro++=0x80|'a';
- else if(ch=='{')
- *making_macro++=0x80|'b';
- else
- *making_macro++=ch;
- if(making_macro>=making_macro_start+making_macro_size) {
-
- making_macro_start=ck_realloc(making_macro_start,5+making_macro_size*2);
- making_macro=making_macro_start+making_macro_size;
- making_macro_size*=2;
- }
- }
- return ch;
- }
-
- #else
- #if !defined(SIGIO) || defined(AMIGA)
- #undef CTRL(X)
- #undef NC
- #include <curses.h>
-
- int intr1 = 0;
- int intr2 = 0;
- static unsigned char
- real_get_chr FUN0()
- {
- static int saved;
- unsigned char ret;
-
- if(saved) {
- ret=saved-1;
- saved=0;
- goto fini;
- }
- if(auto_recalc) {
- current_cycle++;
- if(!bkgrnd_recalc) {
- while(eval_next_cell())
- ;
- } else {
- int ev;
-
- do {
- #if !defined(AMIGA)
- nodelay(stdscr, TRUE);
- #endif
- while(ev=eval_next_cell())
- if((ret=getch())!=ERR)
- goto fini;
- #ifdef TEST
- else
- intr1++;
- #endif
- #if !defined(AMIGA)
- nodelay(stdscr,FALSE);
- #endif
- redisp();
- ret=getch();
- #ifdef TEST
- if(ret==ERR)
- intr2++;
- #endif
- } while(ret==ERR);
- goto fini;
- }
- }
- redisp();
- ret= getch();
- fini:
- if(making_macro) {
- if(ret==0)
- *making_macro++=0x80|'a';
- else if(ret=='{')
- *making_macro++=0x80|'b';
- else
- *making_macro++=ret;
- if(making_macro>=making_macro_start+making_macro_size) {
-
- making_macro_start=ck_realloc(making_macro_start,5+making_macro_size*2);
- making_macro=making_macro_start+making_macro_size;
- making_macro_size*=2;
- }
- }
- if(ret&0x80) {
- if(ret==0x9b)
- {
- /* this is a test pass travis */
- return 0x9b;
- }
-
- saved=1+(ret&0x7f);
- return CTRL('[');
- }
- return ret;
- }
- #else
-
- #ifdef __STDC__
- volatile
- #endif
- int have_kbd_input = 0;
-
- static char ibuf[100];
- static int i_in,i_cnt;
-
- static unsigned char
- real_get_chr FUN0()
- {
- unsigned char ch;
- static int save;
-
- if(save) {
- ch=save-1;
- save=0;
- goto fini;
- }
- if(i_cnt) {
- ch=ibuf[i_cnt++];
- if(i_cnt==i_in)
- i_cnt=i_in=0;
- goto fini;
- }
- for(;;) {
- if(auto_recalc) {
- current_cycle++;
- if(bkgrnd_recalc) {
- while(!have_kbd_input && eval_next_cell())
- ;
- } else {
- while(eval_next_cell())
- ;
- }
- }
- redisp();
- if(have_kbd_input) {
- int ret;
-
- ret=read(0,ibuf,sizeof(ibuf));
- if(ret==1) {
- have_kbd_input=0;
- ch=ibuf[0];
- goto fini;
- }
- if(ret>1) {
- if(have_kbd_input<=ret)
- have_kbd_input=0;
- else
- have_kbd_input-=ret;
- i_cnt=1;
- i_in=ret;
- ch=ibuf[0];
- goto fini;
- }
- if(ret==0 || (errno!=EWOULDBLOCK && errno!=EINTR))
- return EOF;
- }
- pause();
- }
- fini:
- if(making_macro) {
- if(ch==0)
- *making_macro++=0x80|'a';
- else if(ch=='{')
- *making_macro++=0x80|'b';
- else
- *making_macro++=ch;
- if(making_macro>=making_macro_start+making_macro_size) {
-
- making_macro_start=ck_realloc(making_macro_start,5+making_macro_size*2);
- making_macro=making_macro_start+making_macro_size;
- making_macro_size*=2;
- }
- }
- if(ch&0x80) {
- save=1+(ch&0x7f);
- ch=CTRL('[');
- }
- return ch;
- }
-
- void
- got_sigio FUN1(int,sig)
- {
- have_kbd_input++;
- }
-
- #endif
- #endif
-
- #ifdef TEST
- extern int yydebug;
-
- int debug;
- int dbg_do_stderr;
-
- extern void dbg_print_ref_fm();
-
- static void
- dbg_show_var FUN2(char *,name, struct var *,v)
- {
- char *ptr;
-
- /* if(*cmd && strncmp(cmd,v->var_name,strlen(cmd)))
- continue; */
- if(v->var_flags==VAR_UNDEF)
- ptr="Undefined";
- else if(v->var_flags==VAR_CELL)
- ptr="Cell";
- else if(v->var_flags==VAR_RANGE)
- ptr="Range";
- else
- ptr="*UNKNOWN*";
-
- text_line("%s %s %s ",v->var_name,ptr,range_name(&(v->v_rng)));
- if(!v->var_ref_fm)
- text_line("no refs");
- else
- dbg_print_ref_fm(v->var_ref_fm);
- }
- /* Debugging is very important. That's why there is an entire function to
- handle it. . . :-)
- */
- static void
- do_debug FUN1(char *,cmd)
- {
- CELL *cp;
- char *ptr;
- FILE *output;
- extern struct ref_fm *timer_cells;
- extern struct rng all_rng;
-
- extern void dbg_print_ref_to();
- extern void dbg_print_formula();
- extern void dbg_print_cell EXT1(CELL *);
- extern void dbg_print_cols EXT1(CELLREF);
- extern void dbg_print_rows EXT0();
-
- extern void dbg_print_array EXT0();
- extern void ref_stats EXT0();
-
- extern int fputs();
- extern void text_start();
- extern void text_finish();
-
- output=stdout;
- ptr=cmd;
- switch(*ptr++) {
- case 'd':
- debug=astol(&ptr);
- info_msg("Debug now %d",debug);
- return;
-
- case 'f':
- while(*ptr==' ')
- ptr++;
- freopen(ptr,"w",stderr);
- dbg_do_stderr=0;
- return;
-
- case 'y':
- yydebug= !yydebug;
- return;
-
- case 'E':
- output=stderr;
- break;
-
- default:
- break;
- }
-
- --ptr;
- text_start();
- switch(*ptr++) {
- CELLREF rr,cc;
- int n;
- int todo;
- struct rng rn;
- default:
- print_buf[0]='\0';
- break;
-
- case 'R':
- dbg_print_rows();
- break;
-
- case 'C':
- n=astol(&ptr);
- dbg_print_cols(n);
- break;
-
- case 'p':
- dbg_print_array();
- break;
-
- case 'S':
- ref_stats();
- break;
-
- case 'r':
- todo= *ptr++;
- if(!*ptr)
- find_cells_in_range(&all_rng);
- else {
- get_abs_rng(&ptr,&rn);
- find_cells_in_range(&rn);
- }
- ptr=print_buf;
- while(cp=next_row_col_in_range(&rr,&cc)) {
- text_line("(r%uc%u)",rr,cc);
- if(todo=='f' && cp->cell_refs_from) {
- dbg_print_ref_fm(cp->cell_refs_from);
- } else if(todo=='t' && cp->cell_refs_to) {
- dbg_print_ref_to(cp->cell_refs_to,cp->cell_formula);
- } else if(todo=='c') {
- dbg_print_cell(cp);
- } else if(todo=='e' && cp->cell_formula) {
- dbg_print_formula(cp);
- } else if(todo=='F') {
- text_line("flags %#x cycle %d",cp->cell_flags,cp->cell_cycle);
- }
- }
- break;
-
- case 't':
- #ifdef hp800
- {
- sigset_t sigs;
-
- sigprocmask(0,(void *)0,&sigs);
- text_line("Timer is %sactive, ticks=%lu (%lu), sigs %x.%x.%x.%x.%x.%x.%x.%x",timer_active ? "" : "not ",signal_ticks,signal_ticks/TIMER_MULT,sigs.sigset[0],sigs.sigset[1],sigs.sigset[2],sigs.sigset[3],sigs.sigset[4],sigs.sigset[5],sigs.sigset[6],sigs.sigset[7]);
- dbg_print_ref_fm(timer_cells);
- }
- #else
- text_line("Timer is %sactive, ticks=%lu (%lu)",timer_active ? "" : "not ",signal_ticks,signal_ticks/TIMER_MULT);
- dbg_print_ref_fm(timer_cells);
- #endif
- break;
-
- case 'v':
- while(*ptr==' ')
- ptr++;
- cmd=ptr;
- for_all_vars(dbg_show_var);
- break;
-
- case 'm':
- if(*ptr)
- desc_map(the_maps[atoi(ptr)]);
- break;
-
- case 'w':
- dbg_show_wins();
- break;
- #if defined(SIGIO) && !defined(AMIGA)
- case 'k':
- text_line("i_in %d i_cnt %d have_input %d",i_in,i_cnt,have_kbd_input);
- break;
- #endif
- }
- text_finish();
- }
-
- #endif
-
- void
- init_maps FUN0()
- {
- static char main_name[] = "main";
- static char meta_name[] = "meta";
- static char edit_name[] = "edit";
- static char em_name[] = "edit-meta";
- static char ansi_name[] = "ansi";
- static char digit_name[] = "digit";
-
- extern struct keymap edit_map[];
- extern struct keymap edit_meta_map[];
-
- extern struct cmd_func edit_funcs[];
-
- the_maps=ck_malloc(sizeof(struct keymap *)*6);
- map_names=ck_malloc(sizeof(char *)*6);
- num_maps=6;
- the_maps[0]= &main_map[0];
- the_maps[1]= &meta_map[0];
- the_maps[2]= &edit_map[0];
- the_maps[3]= &edit_meta_map[0];
- the_maps[4]= &ansi_map;
- the_maps[5]= &digit_map;
- map_names[0]=main_name;
- map_names[1]=meta_name;
- map_names[2]=edit_name;
- map_names[3]=em_name;
- map_names[4]=ansi_name;
- map_names[5]=digit_name;
- the_funcs=ck_malloc(sizeof(struct cmd_func *)*2);
- num_funcs=2;
- the_funcs[0]= &cmd_funcs[0];
- the_funcs[1]= &edit_funcs[0];
- }
- static int add_usr_cmds FUN1(struct cmd_func *, new_cmds)
- {
- num_funcs++;
-
- the_funcs=ck_realloc(the_funcs,num_funcs*sizeof(struct cmd_func *));
- the_funcs[num_funcs-1]=new_cmds;
- return num_funcs-1;
- }
- #ifdef USE_DLD
- static int add_usr_maps FUN1(struct keymap **, new_maps)
- {
- int n;
-
- for(n=1;new_maps[n];n++)
- ;
-
- the_maps=ck_realloc(the_maps,(n+num_maps)*sizeof(struct keymap *));
- bcopy(new_maps, &the_maps[num_maps],n*sizeof(struct keymap *));
- num_maps+=n;
- return num_maps-n;
- }
- #endif
-
- int
- main FUN2(int,argc, char **,argv)
- {
- int c;
- int num;
- void got_sig();
-
- myname=argv[0];
-
- __make_backups=1;
- #if !defined(__TURBOC__) && !defined(SYSV)
- setbuffer(stdout,buf,sizeof(buf));
- #endif
- if(argc<2 || strcmp(argv[1],"-q")) {
- if(!getenv("OLEO")) {
- fprintf(stdout,"Oleo version 0.03.2, Copyright (C) 1990 Free Software Foundation, Inc.\n");
- fprintf(stdout,"There is ABSOLUTELY NO WARRANTY for Oleo; see the file COPYING\n");
- fprintf(stdout,"for details. Oleo is free software and you are welcome to distribute\n");
- fprintf(stdout,"copies of it under certain conditions; see the file COPYING to see the\n");
- fprintf(stdout,"conditions.\n\n");
- fflush(stdout);
- sleep(5);
- }
- } else {
- --argc;
- ++argv;
- }
- init_mem();
- init_eval();
- init_refs();
- init_cells();
- init_maps();
- obstack_init(¯o_stack);
-
- c=0;
- if(argc>2 && !strcmp(argv[1],"-f")) {
- --argc;
- ++argv;
- c++;
- }
- open_display(c);
-
- if(argc>2) {
- fprintf(stderr,"Usage: %s [filename]\n",argv[0]);
- exit(1);
- }
- #ifdef USE_DLD
- if(!index(myname,'/')) {
- char *name;
-
- name=dld_find_executable(myname);
- num=dld_init(name);
- free(name);
- } else
- num=dld_init(myname);
- if(num)
- error_msg("dld_init() failed: %s",(dld_errno < 0 || dld_errno > dld_nerr) ? "Unknown error" : dld_errlst[dld_errno]);
- dld_search_path=":/usr/local/lib/oleo:/lib:/usr/lib:/usr/local/lib";
- #endif
-
-
- {
- FILE *fp;
- extern int fclose();
- char *ptr,*home;
- /* would be nice to use ck_fopen, but these files might not
- exist. . . */
-
- home=getenv("HOME");
- if(home) {
- ptr=mk_sprintf("%s/%s",home,RCFILE);
- if(fp=fopen(ptr,"r")) {
- read_cmds_cmd(fp);
- fclose(fp);
- }
- free(ptr);
- }
-
- if(fp=fopen(RCFILE,"r")) {
- read_cmds_cmd(fp);
- fclose(fp);
- }
- if(argc==2) {
- set_line(&in_line[3],argv[1]);
- if(fp=fopen(argv[1],"r")) {
- (*read_file)(fp,0);
- fclose(fp);
- } else
- error_msg("Can't open %s: %s",argv[1],err_msg());
- }
- }
-
- signal(SIGINT,got_sigint);
- #ifdef SIGQUIT
- signal(SIGQUIT,got_sig);
- signal(SIGILL,got_sig);
- signal(SIGEMT,got_sig);
- signal(SIGBUS,got_sig);
- signal(SIGSEGV,got_sig);
- signal(SIGPIPE,got_sig);
- #endif
- #if defined(SIGIO) && !defined(AMIGA)
- signal(SIGIO,got_sigio);
- /* close(0);
- if(open("/dev/tty",0)!=0) {
- fprintf(stderr,"Didn't get 0 when trying to re-open stdin\n");
- exit(1);
- } */
- #ifdef FASYNC
- term_flag=fcntl(0,F_GETFL,FASYNC /* |FNDELAY */);
- c=fcntl(0,F_SETFL,FASYNC /* |FNDELAY */);
- if(c==-1) {
- fprintf(stderr,"Can't turn on FASYNC|FNDELAY on stdin: %s\n",err_msg());
- exit(1);
- }
- #else
- #ifdef FIOSSAIOSTAT
- {
- int i;
-
- ioctl(0,FIOGSAIOSTAT,&i);
- term_flag=i;
- ioctl(0,FIOGNBIO, &i);
- if(i)
- term_flag+=2;
- i=1;
- ioctl(0,FIOSSAIOSTAT,&i);
- /* ioctl(0,FIOSNBIO,&i); */
- i=getpid();
- ioctl(0,FIOSSAIOOWN,&i);
- }
- #endif
- #endif
- #endif
- recenter_cur_win();
-
- for(;;) {
- if(how_many!=1) {
- how_many=1;
- cur_status();
- }
- clear_top_before();
- map_chr(MAIN_MAP);
-
- if(topclear && !rmac)
- clear_top_after();
-
- swtch:
- if(!cur_cmd) {
- error_msg("That key is unbound");
- continue;
- }
- if((cur_cmd->func_flags&NONTOP)==0) {
- error_msg("Command '%s' is not appropriate now.",cur_cmd->func_name);
- continue;
- }
- num=global_cmd(MAIN_MAP);
- if(num==-2)
- error_msg("Command '%s' is *not* appropriate now.",cur_cmd->func_name);
- else if(num>=0) {
- c=num;
- goto swtch;
- }
- }
- }
-
- static FILE *
- open_file FUN3(char *,prompt, struct line *,line, char *,mode)
- {
- FILE *fp;
-
- if(get_inp_line(prompt,line))
- return 0;
- if((fp=xopen_with_backup(line->buf,mode))==0) {
- error_msg("Can't open file '%s':%s",line->buf,err_msg());
- return 0;
- }
- return fp;
- }
-
- static void
- close_file FUN2(struct line *,line, FILE *,fp)
- {
- int num;
-
- if(num=xclose(fp))
- error_msg("Can't close '%s': Error code %d: %s",line->buf,num,err_msg());
- }
-
- /* Deal with point-n-shoot */
- static int
- get_a_range FUN3(char *,whatfor, struct rng *,r, struct line *,line)
- {
- char *ptr;
-
- if(mkrow!=NON_ROW) {
- /* The range has already been selected */
- got_rng:
- set_rng(r,mkrow,mkcol,curow,cucol);
- mkrow=NON_ROW;
- return 0;
- }
- switch(get_inp_line(whatfor,line)) {
- case 0:
- if(mkrow!=NON_ROW)
- goto got_rng;
- ptr=line->buf;
- if(get_abs_rng(&ptr,r) || *ptr!='\0') {
- error_msg("Can't parse '%s'",line->buf);
- return 1;
- }
- return 0;
- case 1:
- if(mkrow!=NON_ROW)
- goto got_rng;
- return 1;
- case 2:
- return 1;
- #ifdef TEST
- default:
- panic("Get_inp_line() what?");
- #endif
- }
- return 1;
- }
-
- static FILE *
- get_range_and_file FUN3(char *,whatfor, struct rng *,r, struct line *,line)
- {
- char *ptr;
- char *prompt;
- int got_rng = 0;
- FILE *ret;
- extern char *strdup();
-
- if(mkrow!=NON_ROW) {
- /* We've got the range, just get the file */
- set_rng(r,mkrow,mkcol,curow,cucol);
- got_rng++;
- mkrow=NON_ROW;
- prompt=mk_sprintf("%s %s to file",whatfor,range_name(r));
- } else
- prompt=strdup(whatfor);
-
- if(get_inp_line(prompt,line)) {
- free(prompt);
- return 0;
- }
- free(prompt);
-
- if(mkrow!=NON_ROW) {
- if(got_rng) {
- error_msg("Two ranges?");
- return 0;
- }
- set_rng(r,mkrow,mkcol,curow,cucol);
- mkrow=NON_ROW;
- got_rng++;
- }
- ptr=line->buf;
- if(!got_rng) {
- if(get_abs_rng(&ptr,r)) {
- error_msg("Can't parse '%s'",line->buf);
- return 0;
- }
- if(*ptr==',')
- ptr++;
- }
- while(*ptr==' ')
- ptr++;
- if(!*ptr)
- return 0;
- ret=xopen_with_backup(ptr,"w");
- if(!ret)
- error_msg("Can't open file '%s':%s",ptr,err_msg());
- return ret;
- }
-
- static int
- get_two_ranges FUN4(char *,whatfor, struct rng *,one, struct rng *,two, struct line *,line)
- {
- char *ptr;
- char *prompt;
- int num_got = 0;
- int n;
-
- prompt=0;
- if(mkrow!=NON_ROW) {
- /* We've got the first one already */
- set_rng(one,mkrow,mkcol,curow,cucol);
- mkrow=NON_ROW;
- num_got++;
- }
-
- while(num_got!=2) {
- prompt = (num_got==1) ? mk_sprintf("%s %s to",whatfor,range_name(one)) : whatfor;
- n=get_inp_line(prompt,line);
- if(prompt!=whatfor)
- free(prompt);
-
- if(n>1 || (n==1 && mkrow==NON_ROW))
- return 1;
-
- if(mkrow!=NON_ROW) {
- if(line->buf[0]) {
- error_msg(num_got ? "Extra characters '%s'" : "'%s' is ambiguous", line->buf);
- return 1;
- }
- set_rng(num_got ? two : one, mkrow,mkcol,curow,cucol);
- mkrow=NON_ROW;
-
- num_got++;
- } else {
- ptr=line->buf;
- if(!num_got) {
- if(get_abs_rng(&ptr,one)) {
- error_msg("Can't parse first range in '%s'",line->buf);
- return 1;
- }
- if(*ptr==',')
- ptr++;
- }
-
- if(get_abs_rng(&ptr,two)) {
- if(num_got) {
- error_msg("Can't find second range in '%s'",line->buf);
- return 1;
- }
- num_got++;
- } else if(!num_got)
- num_got+=2;
- else
- num_got++;
- }
- }
- if(*ptr) {
- error_msg("Extra characters in '%s'",line->buf);
- return 1;
- }
-
- sprint_line(line,"%s %s",range_name(one),range_name(two));
- return 0;
- }
-
- /* Read a character. If we're in a macro, read from the macro. . . */
- int
- get_chr FUN0()
- {
- unsigned int ch;
-
- #ifdef TEST
- extern CELL *my_cell;
-
- if(my_cell)
- error_msg("Something didn't clear my_cell!");
- #endif
- if(rmac) {
- ch= *(rmac->mac_exe++);
- switch(ch) {
- case '{': /* What else can we do? */
- case '\0':
- --(rmac->mac_exe);
- break;
-
- case (0x80|'a'):
- ch=0;
- break;
-
- case (0x80|'b'):
- ch='{';
- break;
- default:
- break;
- }
- } else
- ch=real_get_chr();
- return ch;
- }
-
- void
- map_chr FUN1(int, map)
- {
- unsigned int ch;
- struct keymap *keymap;
- struct key *key;
- #ifdef TEST
- extern CELL *my_cell;
-
- if(my_cell)
- error_msg("Something didn't clear my_cell!");
- #endif
- keymap= the_maps[map];
- for(;;) {
- /* ch=get_chr(); */
- if(rmac) {
- int len;
- unsigned char *ptr;
-
- tryagain:
- ch= *(rmac->mac_exe++);
- switch(ch) {
- case '\0':
- cur_vector=0;
- cur_cmd= &cmd_funcs[END_MACRO];
- cur_chr=0;
- return;
-
- case 0x80|'a':
- ch='\0';
- break;
-
- case 0x80|'b':
- ch='{';
- break;
-
- case '{':
- for(ptr=rmac->mac_exe;*ptr && *ptr!=' ' && *ptr!='}';ptr++)
- ;
- len=ptr-rmac->mac_exe;
- for(cur_vector=0;cur_vector<num_funcs;cur_vector++)
- for(cur_cmd= &the_funcs[cur_vector][0];cur_cmd->func_name;cur_cmd++)
- if(!strincmp((char *)(rmac->mac_exe),cur_cmd->func_name,len) && cur_cmd->func_name[len]=='\0') {
- cur_chr='\0';
- goto out;
- }
- error_msg("Ignoring unknown function '%.*s' in macro",len,rmac->mac_exe);
- while(*ptr!='\0' && *ptr!='}')
- ptr++;
- if(*ptr=='}')
- ptr++;
- rmac->mac_exe=ptr;
- goto tryagain;
-
- out:
- if(*ptr==' ') {
- /* ... add argument support here ... */
- if(!cur_cmd->func_args) {
- error_msg("Ignoring extra operand to %s",cur_cmd->func_name);
- while(*ptr && *ptr!='}')
- ptr++;
- if(*ptr=='}')
- ptr++;
- } else if(cur_cmd->func_args[0]=='n') {
- how_many=astol((char **)(&ptr));
- if(*ptr=='}')
- ptr++;
- } else {
- macro_func_arg=(char *)ptr;
- while(*ptr && *ptr!='}')
- ptr++;
- if(*ptr=='}')
- *ptr++='\0';
- }
- rmac->mac_exe=ptr;
- } else
- rmac->mac_exe+=len+1;
- return;
- }
- } else
- ch=real_get_chr();
- for(;;) {
- if(ch>=keymap->lochr && ch<=keymap->hichr) {
- key= keymap->map_dense ? keymap->keys : &(keymap->keys[ch-keymap->lochr]);
- if(key->vector==255) {
- keymap=the_maps[key->code];
- break;
- }
- if(key->vector!=0 || key->code!=0) {
- cur_vector=key->vector;
- cur_cmd= &(the_funcs[key->vector][key->code]);
- cur_chr=ch;
- return;
- }
- }
- if (!(keymap=keymap->map_next)) {
- /* Searched through all the keymaps, and didn't find a match */
- cur_vector=0;
- cur_cmd=0;
- cur_chr=ch;
- return;
- }
- }
- }
- }
-
- /* Return values:
- -3 break key!
- -2 c is inappropriate
- -1 C is OK
- 0+ New char value is ret-1;
- */
-
- int
- global_cmd FUN1(int,magic)
- {
- char *ptr;
- struct rng fm,to;
- FILE *fp;
- static struct line confirm;
- struct cmd_func *cmd;
-
- if(!cur_cmd)
- return -2;
- cmd=cur_cmd;
- if(cmd->func_args) {
- ptr=cmd->func_args;
-
- next_arg:
- switch(*ptr++) {
- case 'R':
- if(get_two_ranges(cmd->func_name,&fm,&to,&in_line[*ptr++-'a']))
- break;
- (*cmd->func_func)(&fm,&to);
- break;
-
- case 'r':
- if(get_a_range(cmd->func_name,&to,&in_line[*ptr++-'a']))
- break;
- (*cmd->func_func)(&to);
- break;
-
- case 't':
- if(get_inp_line(cmd->func_name,&in_line[*ptr++-'a']))
- break;
- (*cmd->func_func)(in_line[cmd->func_args[1]-'a'].buf);
- break;
-
- case 'C':
- if(modified==0)
- goto next_arg;
- set_line(&confirm,0);
- if( get_inp_line("Are you SURE",&confirm)
- || (confirm.buf[0]!='Y' && confirm.buf[0]!='y'))
- return -1;
- goto next_arg;
-
- case 'f':
- fp=open_file(cmd->func_name,&in_line[*ptr-'a'],ptr+1);
- if(!fp)
- break;
- (*cmd->func_func)(fp);
- close_file(&in_line[*ptr++-'a'],fp);
- break;
-
- case 'F':
- fp=get_range_and_file(cmd->func_name,&to,&in_line[*ptr-'a']);
- if(!fp)
- break;
- (*cmd->func_func)(fp,&to);
- close_file(&in_line[*ptr++-'a'],fp);
- break;
-
- case 'n':
- if(!*ptr)
- (*cmd->func_func)();
- else if(*ptr>='0' && *ptr<='9')
- (*cmd->func_func)(*ptr-'0');
- else if(*ptr>='a' && *ptr<='z')
- (*cmd->func_func)((*ptr-'a')*26+ptr[1]-'a');
- else
- (*cmd->func_func)();
- break;
-
- case 'T':
- if(*ptr>='0' && *ptr<='9')
- (*cmd->func_func)(*ptr-'0',cur_chr);
- else
- (*cmd->func_func)();
- break;
-
- case 'N':
- (*cmd->func_func)(magic);
- return cur_chr;
-
- case '\0':
- (*cmd->func_func)();
- break;
-
- #ifdef TEST
- default:
- panic("Unknown arg type %s in global_cmd",ptr);
- #endif
- }
- if(cmd->func_flags&BRK)
- return -3;
- return -1;
- } else if(cmd->func_func) {
- if(cmd->func_flags&WTH_CHR)
- (*cmd->func_func)(cur_chr);
- else
- (*cmd->func_func)();
- if(cmd->func_flags&BRK)
- return -3;
- return -1;
- }
- return -2;
- }
-
- static void
- write_keys_cmd FUN1(FILE *,fp)
- {
- struct keymap *map;
- int n;
- int key;
- int vec;
- int code;
-
- for(n=0;n<num_maps;n++) {
- char *def;
-
- for(map=the_maps[n];map && !map->map_end;map=map->map_next)
- ;
- def=0;
- if(map && map->map_next) {
- for(key=0;key<num_maps;key++)
- if(the_maps[key]==map->map_next) {
- def=map_names[key];
- break;
- }
- }
- if(def)
- fprintf(fp,"create-keymap %s %s\n",map_names[n],def);
- else
- fprintf(fp,"create-keymap %s\n",map_names[n]);
- }
- for(n=0;n<num_maps;n++) {
- for(map=the_maps[n];map;map=map->map_next) {
- for(key=map->lochr;key<=map->hichr;key++) {
- if(map->map_dense) {
- vec=map->keys[0].vector;
- code=map->keys[0].code;
- } else {
- vec=map->keys[key-map->lochr].vector;
- code=map->keys[key-map->lochr].code;
- }
- if(vec==255)
- fprintf(fp,"bind-key %s %s %s\n",
- map_names[n],
- map_names[code],
- char_to_string(key));
- else if(vec || code)
- fprintf(fp,"bind-key %s %s %s\n",
- map_names[n],
- the_funcs[vec][code].func_name,
- char_to_string(key));
- }
- if(map->map_end)
- map=0;
- }
- }
- }
-
- static void
- clear_keymap FUN1(struct keymap *,m)
- {
- int n;
-
- while(m) {
- if(m->map_malloc) {
- if(m->map_dense) {
- m->keys[0].vector=0;
- m->keys[0].code=0;
- m->hichr=m->lochr;
- } else {
- for(n=0;n<=m->hichr-m->lochr;n++) {
- m->keys[n].vector=0;
- m->keys[n].code=0;
- }
- }
- } else {
- m->keys=ck_malloc(sizeof(struct key)*(1+m->hichr-m->lochr));
- for(n=0;n<=m->hichr-m->lochr;n++) {
- m->keys[n].vector=0;
- m->keys[n].code=0;
- }
- m->map_malloc=2;
- }
- if(m->map_end)
- break;
- m=m->map_next;
- }
- }
-
- static void
- make_keymap FUN1(char *,mapname)
- {
- char *ptr;
- int num;
- struct keymap *linkmap;
- extern char *strdup();
-
- for(ptr=mapname;*ptr && *ptr!=' ';ptr++)
- ;
- linkmap=0;
- if(*ptr) {
- *ptr++='\0';
- for(num=0;num<num_maps;num++) {
- if(!strcmp(map_names[num],ptr)) {
- linkmap=the_maps[num];
- break;
- }
- }
- }
- for(num=0;num<num_maps;num++) {
- if(!strcmp(map_names[num],mapname)) {
- clear_keymap(the_maps[num]);
- return;
- }
- }
-
- the_maps=ck_realloc(the_maps,(num_maps+1)*sizeof(struct keymap *));
- the_maps[num_maps]=ck_malloc(sizeof(struct keymap));
- the_maps[num_maps]->map_next=linkmap;
- the_maps[num_maps]->map_end=1;
- the_maps[num_maps]->map_dense=1;
- the_maps[num_maps]->lochr='\0';
- the_maps[num_maps]->hichr='\0';
- the_maps[num_maps]->keys=ck_malloc(sizeof(struct key));
- the_maps[num_maps]->keys[0].vector=0;
- the_maps[num_maps]->keys[0].code=0;
-
-
- map_names=ck_realloc(map_names,(num_maps+1)*sizeof(char *));
- map_names[num_maps]=strdup(mapname);
- num_maps++;
- }
-
-
- static void
- read_cmds_cmd FUN1(FILE *,fp)
- {
- char *ptr;
-
- while(fgets(print_buf,300,fp)) {
- if(ptr=rindex(print_buf,'\n'))
- *ptr='\0';
- execute_cmd(print_buf);
- }
- }
-
- static void
- write_cmd FUN1(FILE *,fp)
- {
- (*write_file)(fp,0);
- modified=0;
- }
-
- static void
- read_cmd FUN1(FILE *,fp)
- {
- (*read_file)(fp,0);
- }
-
- static void
- read_merge_cmd FUN1(FILE *,fp)
- {
- (*read_file)(fp,1);
- }
-
- static void
- write_reg_cmd FUN2(FILE *,fp,struct rng *,rng)
- {
- (*write_file)(fp,rng);
- }
-
- static void
- sort_region_cmd FUN1(char *,ptr)
- {
- struct cmp {
- char mult;
- CELLREF row;
- CELLREF col;
- };
-
- struct rng tmp_rng;
-
- extern struct rng sort_rng;
- extern struct rng sort_ele;
- extern struct cmp *sort_keys;
- extern int sort_keys_num;
- extern int sort_keys_alloc;
- extern void sort_region EXT0();
-
- if(get_abs_rng(&ptr,&sort_rng)) {
- error_msg("Can't find a range to sort in %s", ptr);
- return;
- }
-
- cur_row=sort_rng.lr;
- cur_col=sort_rng.lc;
-
- while(*ptr==' ')
- ptr++;
- if(!*ptr) {
- sort_ele.lr=0;
- sort_ele.lc=0;
- sort_ele.hr=0;
- sort_ele.hc=0;
- } else if(!parse_cell_or_range(&ptr,&sort_ele)) {
- error_msg("Can't parse elements in %s",ptr);
- return;
- } else {
- sort_ele.lr-=sort_rng.lr;
- sort_ele.lc-=sort_rng.lc;
- sort_ele.hr-=sort_rng.lr;
- sort_ele.hc-=sort_rng.lc;
- }
-
- sort_keys_num=0;
- while(*ptr==' ')
- ptr++;
- for(;*ptr;) {
- if(sort_keys_num==sort_keys_alloc) {
- sort_keys_alloc++;
- if(sort_keys_alloc>1)
- {
-
- sort_keys=ck_realloc(sort_keys,sort_keys_alloc*sizeof(struct cmp));
- }
- else
- sort_keys=ck_malloc(sizeof(struct cmp));
- }
- sort_keys[sort_keys_num].mult=1;
- if(*ptr=='+')
- ptr++;
- else if(*ptr=='-') {
- sort_keys[sort_keys_num].mult= -1;
- ptr++;
- }
- if(!*ptr) {
- sort_keys[sort_keys_num].row=0;
- sort_keys[sort_keys_num].col=0;
- sort_keys_num++;
- break;
- }
- if(!parse_cell_or_range(&ptr,&tmp_rng) || tmp_rng.lr!=tmp_rng.hr || tmp_rng.lc!=tmp_rng.hc) {
- error_msg("Can't parse key #%d in %s",sort_keys_num+1,ptr);
- sort_keys_num= -1;
- return;
- }
- sort_keys[sort_keys_num].row=tmp_rng.lr - sort_rng.lr;
- sort_keys[sort_keys_num].col=tmp_rng.lc - sort_rng.lc;
- sort_keys_num++;
-
- while(*ptr==' ')
- ptr++;
- }
- if(sort_keys_num==0) {
- if(sort_keys_alloc==0) {
- sort_keys_alloc++;
- sort_keys=ck_malloc(sizeof(struct cmp));
- }
- sort_keys[0].mult=1;
- sort_keys[0].row=0;
- sort_keys[0].col=0;
- sort_keys_num++;
- }
- sort_region();
- disp_scrn();
- }
-
- static void
- set_var FUN1(char *,ptr)
- {
- int num;
- char *ret;
- extern char *new_var_value EXT3(char *, int, char *);
-
- while(*ptr==' ')
- ptr++;
- for(num=0;ptr[num] && ptr[num]!=' ';num++)
- ;
- modified=1;
- if(!ptr[num])
- ret=new_var_value(ptr,num,(char *)0);
- else
- ret=new_var_value(ptr,num,&ptr[num+1]);
- if(ret)
- error_msg("Can't set-variable %s: %s\n",ptr,ret);
- }
-
- static void
- show_var FUN1(char *,ptr)
- {
- struct var *v;
- int num;
-
- while(*ptr==' ')
- ptr++;
- for(num=0;ptr[num] && ptr[num]!=' ';num++)
- ;
-
- v=find_var(ptr,num);
- if(!v || v->var_flags==VAR_UNDEF) {
- error_msg("There is no '%s'",ptr);
- return;
- }
- #ifdef A0_REFS
- if(v->v_rng.lr!=v->v_rng.hr || v->v_rng.lc!=v->v_rng.hc)
- /* FOO */sprintf(print_buf,"%s $%s$%u:$%s$%u",v->var_name,col_to_str(v->v_rng.lc),v->v_rng.lr,col_to_str(v->v_rng.hc),v->v_rng.hr);
- else
- /* FOO */sprintf(print_buf,"%s $%s$%u",v->var_name,col_to_str(v->v_rng.lc),v->v_rng.lr);
- #else
- sprintf(print_buf,"%s %s",v->var_name,range_name(&(v->v_rng)));
- #endif
- info_msg(print_buf);
- set_line(&in_line[1],print_buf);
- }
-
- static void
- show_a_var FUN2(char *,name, struct var *,v)
- {
- if(v->var_flags==VAR_UNDEF)
- return;
- #ifdef A0_REFS
- if(v->v_rng.lr!=v->v_rng.hr || v->v_rng.lc!=v->v_rng.hc)
- /* FOO */text_line("%-20s $%s$%u:$%s$%u",v->var_name,col_to_str(v->v_rng.lc),v->v_rng.lr,col_to_str(v->v_rng.hc),v->v_rng.hr);
- else
- /* FOO */text_line("%-20s $%s$%u",v->var_name,col_to_str(v->v_rng.lc),v->v_rng.lr);
- #else
- text_line("%-20s %s",v->var_name,range_name(&(v->v_rng)));
- #endif
- }
-
- static void
- show_all_var FUN0()
- {
- extern void text_start EXT0();
- extern void text_finish EXT0();
-
- text_start();
- for_all_vars(show_a_var);
- text_finish();
- }
-
- static void
- shift_cell_cursor FUN1(int, dirn)
- {
- CELLREF c;
- int w = 0;
- int over,down;
-
- over=colmagic[dirn]*how_many;
- down=rowmagic[dirn]*how_many;
- if(over>0) {
- c=cucol;
- while(c<MAX_COL && over-->0) {
- c++;
- while((w=get_width(c))==0 && c<MAX_COL)
- c++;
- }
- if(over>0 || c==cucol || w==0) {
- error_msg("Can't go right");
- return;
- }
- } else if(over<0) {
- c=cucol;
- while(c>MIN_COL && over++<0) {
- --c;
- while((w=get_width(c))==0 && c>MIN_COL)
- --c;
- }
- if(over<0 || c==cucol || w==0) {
- error_msg("Can't go left");
- return;
- }
- } else
- c = cucol;
- if(down>0) {
- if(curow>MAX_ROW-down) {
- error_msg("Can't go down");
- return;
- }
- } else if(down<0) {
- if(curow<MIN_ROW-down) {
- error_msg("Can't go up");
- return;
- }
- }
- move_cell_cursor(curow+down,c);
- }
-
- static void
- scan_cell_cursor FUN1(int,magic)
- {
- CELLREF pos,pos_end,pos_inc;
- CELL *cp;
- int over,down;
-
- extern CELLREF max_row(),max_col();
-
- over=colmagic[magic]*how_many;
- down=rowmagic[magic]*how_many;
- if(over) {
- if(over>0) {
- pos=max_col(curow);
- pos_end=MIN_COL;
- pos_inc= -1;
- } else {
- pos=MIN_COL;
- pos_end=max_col(curow);
- pos_inc=1;
- }
- for(;;) {
- for(;((!(cp=find_cell(curow,pos)) || !GET_TYP(cp)));pos+=pos_inc) {
- if(pos==pos_end) {
- how_many=1;
- pos=MIN_COL;
- break;
- }
- }
- if(--how_many==0)
- break;
- pos+=pos_inc;
- }
- move_cell_cursor(curow,pos);
- } else {
- if(down>0) {
- pos=max_row(cucol);
- pos_end=MIN_ROW;
- pos_inc= -1;
- } else {
- pos=MIN_ROW;
- pos_end=max_row(cucol);
- pos_inc=1;
- }
- for(;;) {
- for(;(!(cp=find_cell(pos,cucol)) || !GET_TYP(cp));pos+=pos_inc) {
- if(pos==pos_end) {
- how_many=1;
- pos=MIN_ROW;
- break;
- }
- }
- if(--how_many==0)
- break;
- pos+=pos_inc;
- }
-
- move_cell_cursor(pos,cucol);
- }
- }
-
-
- char *
- fmt_to_str FUN1(int, fmt)
- {
- char *ptr;
- static char buf[30];
- char nbuf[10];
-
- if(fmt==FMT_DEF)
- return "default";
- if(fmt==FMT_HID)
- return "hidden";
- if(fmt==FMT_GPH)
- return "graph";
- if((fmt&PRC_FLT)==PRC_FLT)
- strcpy(nbuf,"float");
- else
- sprintf(nbuf,"%d",(fmt&PRC_FLT));
- switch(fmt|PRC_FLT) {
- case FMT_USR:
- ptr="user-";
- sprintf(nbuf,"%d",(fmt&PRC_FLT)+1);
- break;
- case FMT_GEN:
- ptr="general.";
- break;
- case FMT_DOL:
- ptr="dollar.";
- break;
- case FMT_CMA:
- ptr="comma.";
- break;
- case FMT_PCT:
- ptr="percent.";
- break;
- case FMT_FXT:
- if((fmt&PRC_FLT)==0)
- return "integer";
- if(fmt==FMT_FXT)
- return "decimal";
- ptr="fixed.";
- break;
- case FMT_EXP:
- ptr="exponent.";
- break;
- default:
- error_msg("Unknown format %d (%x)",fmt,fmt);
- ptr="UNKNOWN";
- break;
- }
- sprintf(buf,"%s%s",ptr,nbuf);
- return buf;
- }
-
- struct fmt {
- int fmt;
- char **strs;
- };
-
- static char *def_names[] = {"default","def","D",0};
- static char *hid_names[] = {"hidden","hid","H",0};
- static char *gph_names[] = {"graph","gph","*",0};
- static char *int_names[] = {"integer","int","I",0};
- static char *dec_names[] = {"decimal","dec",0};
-
- static struct fmt simple[] = {
- { FMT_DEF, def_names },
- { FMT_HID, hid_names },
- { FMT_GPH, gph_names },
- { FMT_FXT-PRC_FLT, int_names },
- { FMT_FXT, dec_names },
- { 0, 0}
- };
-
- char *gen_names[] = {"general.","gen.","G",0};
- char *dol_names[] = {"dollar.","dol.","$",0};
- char *cma_names[] = {"comma.","com.",",",0};
- char *pct_names[] = {"percent.","pct.","%",0};
- char *fxt_names[] = {"fixed.","fxt.","F",0};
- char *exp_names[] = {"exponent.","exp.","E",0};
-
- static struct fmt withprec[] = {
- { FMT_GEN-PRC_FLT, gen_names },
- { FMT_DOL-PRC_FLT, dol_names },
- { FMT_CMA-PRC_FLT, cma_names },
- { FMT_PCT-PRC_FLT, pct_names },
- { FMT_FXT-PRC_FLT, fxt_names },
- { FMT_EXP-PRC_FLT, exp_names },
- { 0, 0 }
- };
-
- static int
- str_to_fmt FUN1(char *,ptr)
- {
- struct fmt *f;
- char **strs;
- int n;
- int ret;
- char *p1,*p2;
-
- for(f=simple;f->strs;f++) {
- for(strs=f->strs;*strs;strs++) {
- if(*ptr!=**strs)
- continue;
- for(p1=ptr,p2= *strs;*p1==*p2 && *p1;p1++,p2++)
- ;
- if(*p1=='\0' && *p2=='\0')
- return f->fmt;
- }
- }
- if(!strncmp(ptr,"user-",5)) {
- ptr+=5;
- n=astol(&ptr);
- if(*ptr || n<1 || n>16)
- return -1;
- return n-1-PRC_FLT+FMT_USR;
- }
- for(f=withprec,ret=0;!ret && f->strs;f++) {
- for(strs=f->strs;*strs;strs++) {
- if(*ptr!=**strs)
- continue;
- for(p1=ptr,p2= *strs;*p2 && *p1==*p2;p1++,p2++)
- ;
- if(!*p2) {
- ret=f->fmt;
- ptr=p1;
- break;
- }
- }
- }
-
- if(!ret || !*ptr)
- return -1;
- if(!strcmp(ptr,"float") || !strcmp(ptr,"f")) {
- n=PRC_FLT;
- } else {
- n=astol(&ptr);
- if(*ptr || n<0 || n>14)
- return -1;
- }
- return ret+n;
- }
-
- char *
- jst_to_str FUN1(int, jst)
- {
- if(jst==JST_DEF)
- return "default";
- if(jst==JST_LFT)
- return "left";
- if(jst==JST_RGT)
- return "right";
- if(jst==JST_CNT)
- return "center";
- return "unknown";
- }
-
- static int
- chr_to_jst FUN1(int, chr)
- {
- if(chr=='d' || chr=='D')
- return JST_DEF;
- if(chr=='l' || chr=='L')
- return JST_LFT;
- if(chr=='r' || chr=='R')
- return JST_RGT;
- if(chr=='c' || chr=='C')
- return JST_CNT;
- return -1;
- }
-
- /* parse a range, then turn it into an absolute rng */
- static int
- get_abs_rng FUN2(char **,pptr, struct rng *,retp)
- {
- unsigned char n;
-
- while(**pptr==' ')
- (*pptr)++;
- if(!**pptr)
- return 1;
- cur_row=curow;
- cur_col=cucol;
- n=parse_cell_or_range(pptr,retp);
- if(!n) {
- struct var *v;
- char *ptr;
-
- ptr= *pptr;
- while(ptr[n] && ptr[n]!=' ')
- n++;
- v=find_var(ptr,n);
- if(!v)
- return 1;
- (*pptr)+=n;
- *retp= v->v_rng;
- }
- return 0;
- }
-
- static void desc_map FUN1(struct keymap *,map)
- {
- int n;
- int maxn;
-
-
- text_start();
- while(map) {
- maxn=1+map->hichr-map->lochr;
- if(map->map_dense)
- text_line("%s - %s: %d %d %s",
- char_to_string(map->lochr),
- char_to_string(map->hichr),
- map->keys[0].vector,
- map->keys[0].code,
- map->keys[0].vector==255 ? "vector" : the_funcs[map->keys[0].vector][map->keys[0].code].func_name);
- else
- for(n=0;n<maxn;n++)
- text_line("%s: %d %d %s",
- char_to_string(map->lochr+n),
- map->keys[n].vector,
- map->keys[n].code,
- map->keys[n].vector==255 ? "vector" : the_funcs[map->keys[n].vector][map->keys[n].code].func_name);
- map=map->map_end ? 0 : map->map_next;
- }
- text_finish();
- }
-
- #if 0
- static char *
- key_name FUN1(int,key)
- {
- /* int mac;
-
- if(main_map[key]==BOUND_MACRO) {
- for(mac=0;mac<n_bound_macros;mac++)
- if(bound_macros[mac].c==key)
- return range_name(&(bound_macros[mac].r));
- #ifdef TEST
- error_msg("Unknown bound macro on key %d",key);
- #endif
- }
- return cmd_funcs[main_map[key]].func_name; */
- }
- #endif
-
- static void
- set_usr_fmt FUN1(char *,fmtstr)
- {
- int u_num;
- char *ptr;
- static struct line usr_line;
- struct line tmp_line;
- char *tmp_ptr;
- char *data_buf[9];
- int i;
- static char *names[9]= {
- "Positive header",
- "Negative header",
- "Positive trailer",
- "Negative trailer",
- "Zero",
- "Comma",
- "Decimal point",
- "Precision",
- "Scale-factor"
- };
-
- tmp_line.buf=ck_malloc(10);
- tmp_line.alloc=10;
- tmp_ptr=tmp_line.buf;
-
- ptr=fmtstr;
- u_num=astol(&ptr);
- if(u_num<1 || u_num>16 || *ptr!='\0') {
- error_msg("Unknown number %s",fmtstr);
- return;
- }
- --u_num;
-
- get_usr_stats(u_num,data_buf);
- for(i=0;i<9;i++) {
- int slen;
- int prevlen;
-
- set_line(&usr_line,data_buf[i]);
- if(get_inp_line(names[i],&usr_line)>1)
- return;
-
- slen=strlen(usr_line.buf);
- if(tmp_line.alloc<=(tmp_ptr-tmp_line.buf)+slen) {
- prevlen=tmp_ptr-tmp_line.buf;
- tmp_line.alloc+=slen+1;
-
- tmp_line.buf=ck_realloc(tmp_line.buf,tmp_line.alloc);
- tmp_ptr=tmp_line.buf+prevlen;
- }
- strcpy(tmp_ptr,usr_line.buf);
- data_buf[i]=tmp_ptr;
- while(*tmp_ptr!='\0')
- tmp_ptr++;
- tmp_ptr++;
- }
-
- set_usr_stats(u_num, data_buf);
- free(tmp_line.buf);
- disp_scrn();
- }
-
-
- /* Modify this to write out *all* the options */
- void
- write_mp_options FUN1(FILE *,fp)
- {
- fprintf(fp,"O;%sauto;%sbackground;ticks %d\n",
- auto_recalc ? "" : "no",
- bkgrnd_recalc ? "" : "no",
- signal_ticks/TIMER_MULT);
- }
-
- void
- read_mp_options FUN1(char *,str)
- {
- char *np;
-
- while(np=index(str,';')) {
- *np='\0';
- (void)do_set_option(str);
- *np++=';';
- str=np;
- }
- if(np=rindex(str,'\n'))
- *np='\0';
- (void)do_set_option(str);
- }
-
- void
- set_options FUN1(char *,ptr)
- {
- if(do_set_option(ptr))
- recenter_cur_win();
- }
-
- static void
- show_options FUN0()
- {
- int n;
- int fmts;
- char *data_buf[9];
-
- extern char *strdup();
- extern void text_start EXT0();
- extern void text_finish EXT0();
- extern void show_window_options();
-
- n=auto_recalc;
- text_start();
-
- text_line("auto-recalculation: %s Recalculate in background: %s",
- n ? " on" : "off",bkgrnd_recalc ? "on" : "off");
- text_line("make backup files: %s Copy files into backups: %s",
- __make_backups ? " on" : "off",__backup_by_copying ? "on" : "off");
-
- text_line("Asynchronous updates every %u ???",
- signal_ticks/TIMER_MULT);
-
- text_line("Print width: %5u",print_width);
-
- text_line("");
-
- (*show_file_opts)();
-
- text_line("");
- show_window_options();
- text_line("");
-
- fmts=usr_set_fmts();
- if(fmts) {
- text_line("User-defined formats:");
- text_line("Fmt +Hdr -Hdr +Trlr -Trlr Zero Comma Decimal Prec Scale");
- for(n=0;n<16;n++) {
- if(fmts&(1<<n)) {
- get_usr_stats(n,data_buf);
- text_line("%3d %7s %7s %7s %7s %7s %7s %7s %5s %13s",
- n+1,
- data_buf[0],
- data_buf[1],
- data_buf[2],
- data_buf[3],
- data_buf[4],
- data_buf[5],
- data_buf[6],
- data_buf[7],
- data_buf[8]);
- }
- }
- } else
- text_line("No user-defined formats have been defined");
-
- text_finish();
- }
-
- static int
- do_set_option FUN1(char *,ptr)
- {
- int set_opt = 1;
- extern int set_window_option();
-
- while(*ptr==' ')
- ptr++;
- if(!strincmp("no",ptr,2)) {
- ptr+=2;
- set_opt=0;
- while(*ptr==' ')
- ptr++;
- }
- if(!stricmp("auto",ptr)) {
- auto_recalc = set_opt;
- return 0;
- }
- if(!stricmp("bkgrnd",ptr) || !stricmp("background",ptr)) {
- bkgrnd_recalc = set_opt;
- return 0;
- }
- if(!stricmp("backup",ptr)) {
- __make_backups = set_opt;
- return 0;
- }
- if(!stricmp("bkup_copy",ptr)) {
- __backup_by_copying = set_opt;
- return 0;
- }
- if(set_opt && !strincmp("ticks ",ptr,6)) {
- extern unsigned ualarm EXT2(unsigned int, unsigned int);
-
- ptr+=6;
- signal_ticks= astol(&ptr) * TIMER_MULT;
- #ifndef __TURBOC__
- if(timer_active)
- ualarm(signal_ticks,signal_ticks);
- #endif
- return 0;
- }
- if(set_opt && !strincmp("print ",ptr,6)) {
- ptr+=6;
- print_width=astol(&ptr);
- return 0;
- }
- if(set_opt && !strincmp("file ",ptr,5)) {
- #ifdef USE_DLD
- char *tmpstr;
- extern char *strdup();
-
- ptr+=5;
- tmpstr=ck_malloc(strlen(ptr)+20);
- if(io_name) {
- sprintf(tmpstr, "%s.o", ptr);
- if(dld_unlink_by_file(tmpstr,0)) {
- error_msg("Couldn't unlink old file format %s: %s",io_name,(dld_errno < 0 || dld_errno > dld_nerr) ? "Unknown error" : dld_errlst[dld_errno]);
- goto bad_file;
- }
- free(io_name);
- }
- if(!stricmp(ptr,"panic")) {
- io_name=0;
- read_file = panic_read_file;
- write_file = panic_write_file;
- set_file_opts = panic_set_options;
- show_file_opts = panic_show_options;
- free(tmpstr);
- return 0;
- }
- io_name=strdup(ptr);
- sprintf(tmpstr, "%s.o", ptr);
- if(dld_link(tmpstr)) {
- error_msg("Couldn't link new file format %s: %s",io_name,(dld_errno < 0 || dld_errno > dld_nerr) ? "Unknown error" : dld_errlst[dld_errno]);
- goto bad_file;
- }
- if(dld_link("libc.a"))
- error_msg("Couldn't link libc.a");
- if(dld_link("libm.a"))
- error_msg("Couldn't link libm.a");
-
- sprintf(tmpstr, "%s_read_file",ptr);
- read_file=dld_function_executable_p(tmpstr) ? dld_get_func(tmpstr) : 0;
- sprintf(tmpstr, "%s_write_file",ptr);
- write_file=dld_function_executable_p(tmpstr) ? dld_get_func(tmpstr) : 0;
-
- sprintf(tmpstr, "%s_set_options",ptr);
- set_file_opts=(int(*)())(dld_function_executable_p(tmpstr) ? dld_get_func(tmpstr) : 0);
- sprintf(tmpstr, "%s_show_options",ptr);
- show_file_opts=dld_function_executable_p(tmpstr) ? dld_get_func(tmpstr) : 0;
-
- if( !read_file
- || !write_file
- || !set_file_opts
- || !show_file_opts) {
- char **missing;
- int n;
-
- missing=dld_list_undefined_sym();
- text_start();
- text_line("Undefined symbols in file format %s:",ptr);
- text_line("");
- for(n=0;n<dld_undefined_sym_count;n++)
- text_line("%s",missing[n]);
- text_line("");
- text_finish();
- free(missing);
- error_msg("File format %s has undefined symbols: not loaded",ptr);
- bad_file:
- sprintf(tmpstr, "%s.o",io_name);
- dld_unlink_by_file(io_name,0);
- if(io_name)
- free(io_name);
- io_name=0;
- read_file=panic_read_file;
- write_file=panic_write_file;
- set_file_opts=panic_set_options;
- show_file_opts=panic_show_options;
- }
- free(tmpstr);
- #else
- ptr+=5;
- if(!stricmp("sylk",ptr)) {
- read_file = sylk_read_file;
- write_file = sylk_write_file;
- set_file_opts = sylk_set_options;
- show_file_opts= sylk_show_options;
- } else if(!stricmp("sc",ptr)) {
- read_file = sc_read_file;
- write_file = sc_write_file;
- set_file_opts = sc_set_options;
- show_file_opts= sc_show_options;
- } else if(!stricmp("panic",ptr)) {
- read_file = panic_read_file;
- write_file = panic_write_file;
- set_file_opts = panic_set_options;
- show_file_opts= panic_show_options;
- } else if(!stricmp("list",ptr)) {
- read_file = list_read_file;
- write_file = list_write_file;
- set_file_opts = list_set_options;
- show_file_opts= list_show_options;
- /*if(ptr[4]) {
- ptr+=4;
- sl_sep=string_to_char(&ptr);
- } */
- } else
- error_msg("Unknown file format %s",ptr);
- #endif
- return 0;
- }
- #ifdef USE_DLD
- else if(!strincmp(ptr,"load ",5)) {
- char *tmpstr;
- struct function *new_funs;
- struct cmd_func *new_cmds;
- struct keymap **new_maps;
- void (*init_cmd) EXT0();
-
- extern unsigned long dld_get_symbol EXT1(char *);
- extern void add_usr_funs EXT1(struct function *);
-
- ptr+=5;
- tmpstr=ck_malloc(strlen(ptr)+20);
- sprintf(tmpstr,"%s.o",ptr);
- if(dld_link(tmpstr)) {
- error_msg("Couldn't link %s: %s",tmpstr,(dld_errno < 0 || dld_errno > dld_nerr) ? "Unknown error" : dld_errlst[dld_errno]);
- free(tmpstr);
- return 0;
- }
- if(dld_link("libc.a"))
- error_msg("Couldn't link libc.a");
- if(dld_link("libm.a"))
- error_msg("Couldn't link libm.a");
-
- if(dld_undefined_sym_count) {
- char **missing;
- int n;
-
- missing=dld_list_undefined_sym();
- text_start();
- text_line("Undefined symbols in file format %s:",ptr);
- text_line("");
- for(n=0;n<dld_undefined_sym_count;n++)
- text_line("%s",missing[n]);
- text_line("");
- text_finish();
- free(missing);
- error_msg("%d undefined symbols in %s",dld_undefined_sym_count,ptr);
- dld_unlink_by_file(tmpstr,0);
- free(tmpstr);
- return 0;
- }
- sprintf(tmpstr,"%s_funs",ptr);
- new_funs=(struct function *)dld_get_symbol(tmpstr);
- if(new_funs)
- add_usr_funs(new_funs);
- sprintf(tmpstr,"%s_cmds", ptr);
- new_cmds=(struct cmd_func *)dld_get_symbol(tmpstr);
- if(new_cmds)
- add_usr_cmds(new_cmds);
- sprintf(tmpstr,"%s_maps", ptr);
- new_maps=(struct keymap **)dld_get_symbol(tmpstr);
- if(new_maps)
- add_usr_maps(new_maps);
- if(!new_funs && !new_cmds && !new_maps) {
- error_msg("Couldn't find anything to load in %s",ptr);
- sprintf(tmpstr,"%s.o",ptr);
- dld_unlink_by_file(tmpstr,0);
- }
- sprintf(tmpstr,"%s_init",ptr);
- init_cmd=dld_function_executable_p(tmpstr) ? dld_get_func(tmpstr) : 0;
- if(init_cmd)
- (*init_cmd)();
- free(tmpstr);
- return 0;
- }
- #endif
- if(set_window_option(set_opt,ptr)==0) {
- if((*set_file_opts)(set_opt,ptr))
- error_msg("Unknown option '%s'",ptr);
- return 0;
- }
- return 1;
- }
-
- void
- set_line FUN2(struct line *,line, char *,string)
- {
- int len;
-
- if(!string) {
- if(line->alloc)
- line->buf[0]='\0';
- return;
- }
- len=strlen(string);
- if(line->alloc<=len) {
- if(len<LINE_MIN)
- len=LINE_MIN;
- else
- len++;
- line->alloc=len+1;
- if(line->buf)
- {
-
- line->buf=ck_realloc(line->buf,line->alloc);
- }
- else
- line->buf=ck_malloc(line->alloc);
- }
- strcpy(line->buf,string);
- }
-
- static void
- sprint_line FUN2N(struct line *,line, char *,fmt)
- {
- va_list iggy;
- int len;
-
- len=strlen(fmt)+200;
- if(!line->alloc) {
- line->buf=ck_malloc(len);
- line->alloc=len;
- } else if(line->alloc<len) {
-
- line->buf=ck_realloc(line->buf,len);
- line->alloc=len;
- }
- var_start(iggy,fmt);
- vsprintf(line->buf,fmt,iggy);
- va_end(iggy);
- }
-
- static void
- execute_cmd FUN1(char *,str)
- {
- CELL *cp;
- struct macro *old;
- struct rng r;
- char *ptr;
-
- for(ptr=str;*ptr && *ptr!=' ';ptr++)
- ;
- if(*ptr)
- *ptr++='\0';
- else
- ptr=0;
-
- for(cur_vector=0;cur_vector<num_funcs;cur_vector++)
- for(cur_cmd= &the_funcs[cur_vector][0];cur_cmd->func_name;cur_cmd++)
- if(!stricmp(str,cur_cmd->func_name)) {
- /* these lines stolen from map_char */
- if(ptr) {
- if(!cur_cmd->func_args)
- error_msg("Ignoring extra operand to %s",cur_cmd->func_name);
- else if(cur_cmd->func_args[0]=='n')
- how_many=astol((char **)(&ptr));
- else
- macro_func_arg=ptr;
- }
-
- cur_chr='\0';
- global_cmd(MAIN_MAP);
- return;
- }
-
- if(get_abs_rng(&str,&r)) {
- error_msg("Unknown command %s",str);
- return;
- }
- if(ptr) {
- error_msg("Macros can't take arguments");
- return;
- }
-
- if( !(cp=find_cell(r.lr,r.lc))
- || GET_TYP(cp)!=TYP_STR
- || cp->cell_str[0]=='\0')
- return;
-
- old=rmac;
- rmac=(struct macro *)obstack_alloc(¯o_stack,sizeof(struct macro));
- rmac->mac_prev=old;
- rmac->mac_rng= r;
- rmac->mac_row=r.lr;
- rmac->mac_col=r.lc;
- (void)obstack_grow(¯o_stack,cp->cell_str,1+strlen(cp->cell_str));
- rmac->mac_exe=(unsigned char *)obstack_finish(¯o_stack);
- rmac->mac_flags=0;
- }
-
- static void
- goto_region FUN1(struct rng *,r)
- {
- struct rng tmp;
-
- if(mkrow!=NON_ROW) {
- CELLREF cx,cy;
-
- set_rng(&tmp,curow,cucol,mkrow,mkcol);
- set_line(&in_line[12],range_name(&tmp));
- cx=mkrow;
- mkrow=curow;
- cy=mkcol;
- mkcol=cucol;
- (void)move_cell_cursor(cx,cy);
- } else {
- set_line(&in_line[12],cell_name(curow,cucol));
- (void)move_cell_cursor(r->lr,r->lc);
- }
- if(r->hr!=r->lr || r->hc!=r->lc) {
- mkrow=r->hr;
- mkcol=r->hc;
- cur_status();
- } else if(mkrow!=NON_ROW) {
- mkrow=NON_ROW;
- cur_status();
- }
- }
-
- static void
- set_default FUN0()
- {
- int fun;
- char *ptr;
- int num;
- char buf[20];
-
- sprintf(buf,"%d",default_width);
- set_line(&wid_line,buf);
- set_line(&fmt_line,fmt_to_str(default_fmt));
- info_msg("Alignment %s Format %s %srotected Width %d",
- jst_to_str(default_jst),
- fmt_line.buf,
- default_lock==LCK_LCK ? "P" : "Unp",
- default_width);
-
- fun=get_chr_prompt("[A]lignment, [F]ormat, [P]rotection, or [W]idth ");
- switch(fun) {
- case 'w':
- case 'W':
- if(get_inp_line("set-default-width",&wid_line))
- break;
- ptr=wid_line.buf;
- num=astol(&ptr);
- if(num<1)
- error_msg("Can't set default width to '%s'",wid_line.buf);
- else {
- default_width=num;
- recenter_all_win();
- return;
- }
- break;
-
- case 'p':
- case 'P':
- fun=get_chr_prompt("[P]rotected, or [U]nprotected");
- if(fun=='p' || fun=='P')
- default_lock= LCK_LCK;
- else if(fun=='u' || fun=='U')
- default_lock=LCK_UNL;
- else /* if(main_map<[fun]!=BREAK_CMD) */
- error_msg("Unknown char '%s'",char_to_string(fun));
- break;
-
- case 'f':
- case 'F':
- if(get_inp_line("set-default-format",&fmt_line))
- break;
- num=str_to_fmt(fmt_line.buf);
- if(num==-1 || num==FMT_DEF) {
- error_msg("Unknown format '%s'",fmt_line.buf);
- break;
- }
- default_fmt=num;
- disp_scrn();
- return;
-
- case 'a':
- case 'A':
- fun=get_chr_prompt("[L]eft, [R]ight, or [C]enter");
- num=chr_to_jst(fun);
- if(num!=-1 && num!=JST_DEF) {
- default_jst=num;
- disp_scrn();
- return;
- } else /* if(main_map[fun]!=BREAK_CMD) */
- error_msg("Unknown Alignment '%s'",char_to_string(fun));
- break;
-
- default:
- /* if(main_map[fun]!=BREAK_CMD) */
- error_msg("Unknown command '%s'",char_to_string(fun));
- /* else
- error_msg(""); */
- break;
- }
- cur_status();
- /* topclear=2; */
- }
-
- static void
- format_area FUN1(struct rng *,f)
- {
- int c;
- int fmt,jst,wid;
- CELLREF cc;
- char *locked;
- CELL *cp;
- int fun;
- char *ptr;
- extern unsigned short get_nodef_width EXT1(CELLREF);
-
- cp=find_cell(f->lr,f->lc);
- if(!cp) {
- fmt=FMT_DEF;
- jst=JST_DEF;
- } else {
- fmt=GET_FMT(cp);
- jst=GET_JST(cp);
- }
-
- wid=get_nodef_width(f->lc);
- if(wid==0)
- set_line(&wid_line,"default");
- else
- sprint_line(&wid_line,"%d",wid-1);
-
- set_line(&fmt_line,fmt_to_str(fmt));
- if(cp) {
- if(GET_LCK(cp)==LCK_DEF)
- locked = (default_lock==LCK_UNL ? "default unprotected" : "default protected");
- else if(GET_LCK(cp)==LCK_UNL)
- locked = "unprotected";
- else if(GET_LCK(cp)==LCK_LCK)
- locked = "protected";
- else
- locked = "Huh What?";
- } else
- locked = (default_lock==LCK_UNL ? "default unprotected" : "default protected");
-
- info_msg("Alignment %s Format %s Width %s %s",
- jst_to_str(jst),
- fmt_line.buf,
- wid_line.buf,
- locked);
-
- fun=get_chr_prompt("[A]lignment, [F]ormat, [P]rotection, or [W]idth ");
- switch(fun) {
- case 'f':
- case 'F':
- if(get_inp_line("set-format",&fmt_line))
- break;
- fmt=str_to_fmt(fmt_line.buf);
- if(fmt!=-1)
- format_region(f,fmt,-1);
- else
- error_msg("Unknown format '%s'",fmt_line.buf);
- break;
-
- case 'a':
- case 'A':
- c=get_chr_prompt("Align [L]eft, [R]ight, [C]enter, or [D]efault");
- fun=chr_to_jst(c);
- if(fun!=-1)
- format_region(f,-1,fun);
- else /* if(main_map[c]!=BREAK_CMD) */
- error_msg("Unknown Justify '%s'",char_to_string(c));
- break;
-
- case 'p':
- case 'P':
- c=get_chr_prompt("[D]efault, [P]rotect, or [U]nprotect");
- if(c=='d' || c=='D')
- lock_region(f,LCK_DEF);
- else if(c=='p' || c=='P')
- lock_region(f,LCK_LCK);
- else if(c=='u' || c=='U')
- lock_region(f,LCK_UNL);
- else /* if(main_map[c]!=BREAK_CMD) */
- error_msg("Unknown lock %s",char_to_string(c));
- break;
-
- case 'w':
- case 'W':
- if(get_inp_line("set-width",&wid_line))
- break;
- ptr=wid_line.buf;
- if(*ptr=='d' || *ptr=='D')
- fun=0;
- else if(isdigit(*ptr))
- fun=astol(&ptr)+1;
- else {
- error_msg("Unknown width '%s'",wid_line.buf);
- break;
- }
- for(cc=f->lc;;cc++) {
- set_width(cc,fun);
- if(cc==f->hc)
- break;
- }
- recenter_all_win();
- return;
-
- default:
- /* if(main_map[fun]!=BREAK_CMD) */
- error_msg("Unknown command '%s'",char_to_string(fun));
- break;
- }
- cur_status();
- /* topclear=2; */
- }
-
-
- void
- got_sig FUN0()
- {
- FILE *fp;
- extern int write();
-
- /* Using xopen_with_backup is almost certainly a bad idea, however
- using open() (preferred) or fopen() causes trouble in the restore,
- so we suffer. . . */
-
- fp=xopen_with_backup("oleo.panic","w");
- if(fp) {
- write(1,"Performing panic save to 'oleo.panic'\r\n",39);
- panic_write_file(fp,0);
- xclose(fp);
- } else
- write(1,"Can't open 'oleo.panic'! You lose!\r\n",37);
- close_display();
- #ifdef FASYNC
- fcntl(0,F_SETFL,term_flag);
- #endif
- #ifdef FIOSSAIOSTAT
- if((term_flag&1)==0) {
- int i=0;
-
- ioctl(0,FIOSSAIOSTAT,&i);
- }
- if((term_flag&2)==0) {
- int i=0;
-
- ioctl(0,FIOSNBIO,&i);
- }
- #endif
-
- exit(11);
- }
-
- static void
- got_sigint FUN1(int, ign)
- {
- int ch;
-
- ch=get_chr_prompt("Panic save and exit?");
- if(ch=='y' || ch=='Y')
- got_sig();
- }
-
-
- static void
- start_macro FUN0()
- {
- if(making_macro) {
- error_msg("Can't define two macros at once");
- return;
- }
- making_macro_size=20;
- making_macro=making_macro_start=ck_malloc(5+making_macro_size);
- /* *making_macro++='"'; */
- }
-
- static void
- end_macro FUN0()
- {
- union vals z;
- struct rng to;
- CELL *cp;
- struct macro *old;
- static struct line macro_line;
-
- if(!rmac && !making_macro) {
- error_msg("Not executing or defining a macro!");
- return;
- }
- if(rmac) {
- if(rmac->mac_row==rmac->mac_rng.hr && rmac->mac_col==rmac->mac_rng.hc) {
- old=rmac->mac_prev;
- (void)obstack_free(¯o_stack,rmac);
- rmac=old;
- goto deal_making;
- }
-
- if(rmac->mac_row==rmac->mac_rng.hr) {
- rmac->mac_row=rmac->mac_rng.lr;
- rmac->mac_col++;
- } else
- rmac->mac_row++;
- if(!(cp=find_cell(rmac->mac_row,rmac->mac_col)) || GET_TYP(cp)!=TYP_STR || cp->cell_str[0]=='\0') {
- old=rmac->mac_prev;
- (void)obstack_free(¯o_stack,rmac);
- rmac=old;
- goto deal_making;
- }
- (void)obstack_grow(¯o_stack,cp->cell_str,1+strlen(cp->cell_str));
- rmac->mac_exe=(unsigned char *)obstack_finish(¯o_stack);
- rmac->mac_flags=0;
- }
- deal_making:
- if(!making_macro)
- return;
-
-
- making_macro[0]='\0';
- making_macro=0;
- if(get_a_range("Put macro where",&to,¯o_line))
- error_msg("Forgetting new macro");
- else {
- extern void set_new_value();
- z.c_s=(char *)making_macro_start;
- set_new_value(to.lr,to.lc,TYP_STR,&z);
- }
- free(making_macro_start);
- }
-
- static void
- quit_cmd FUN0()
- {
- int c;
-
- close_display();
- #ifndef AMIGA
- #ifdef FASYNC
- c=fcntl(0,F_SETFL,term_flag);
- #endif
- #ifdef FIOSSAIOSTAT
- if((term_flag&1)==0) {
- int i=0;
-
- ioctl(0,FIOSSAIOSTAT,&i);
- }
- if((term_flag&2)==0) {
- int i=0;
-
- ioctl(0,FIOSNBIO,&i);
- }
- #endif
- #endif
- exit(0);
- }
-
- static void
- bound_macro FUN1(int, num)
- {
- struct macro *old;
- CELL *cp;
- /* CELLREF rr,cc; */
-
- cp=find_cell(bound_macros[num].lr,bound_macros[num].lc);
- if(!cp || GET_TYP(cp)!=TYP_STR || cp->cell_str[0]=='\0')
- return;
- old=rmac;
- rmac=(struct macro *)obstack_alloc(¯o_stack,sizeof(struct macro));
- rmac->mac_prev=old;
- rmac->mac_rng=bound_macros[num];
- rmac->mac_row=bound_macros[num].lr;
- rmac->mac_col=bound_macros[num].lc;
- (void)obstack_grow(¯o_stack,cp->cell_str,1+strlen(cp->cell_str));
- rmac->mac_exe=(unsigned char *)obstack_finish(¯o_stack);
- rmac->mac_flags=0;
- }
-
- static void
- mark_cell_cmd FUN0()
- {
- mkrow=curow;
- mkcol=cucol;
- cur_status();
- }
-
- static void
- recalc_cmd FUN0()
- {
- current_cycle++;
- while(eval_next_cell())
- ;
- }
-
- static void
- desc_key_cmd FUN0()
- {
- error_msg("Key: ");
- map_chr(MAIN_MAP);
- if(!cur_cmd)
- info_msg("%s is unbound", char_to_string(cur_chr));
- else
- info_msg("%s --> %s",char_to_string(cur_chr), cur_cmd->func_name);
- }
-
- static void
- bind_key_cmd FUN1(char *,text)
- {
- int map;
- int c;
- /* int n; */
- int vec;
- int code;
- char *ptr;
- char *cmdstr;
- struct rng rng;
- struct cmd_func *tmpfunc;
- static struct line tmpline;
-
- for(ptr=text;*ptr && *ptr!=' ';ptr++)
- ;
- if(!*ptr) {
- if(get_inp_line("Command",&tmpline))
- return;
- ptr=tmpline.buf;
- } else
- *ptr++='\0';
- while(*ptr==' ')
- ptr++;
- cmdstr=ptr;
- while(*ptr && *ptr!=' ')
- ptr++;
- if(!*ptr)
- c=get_chr_prompt("Key: ");
- else {
- *ptr++='\0';
- c=string_to_char(&ptr);
- }
-
- for(map=0;map<num_maps;map++)
- if(!strcmp(text,map_names[map]))
- break;
- if(map==num_maps) {
- error_msg("Can't find keymap '%s'",text);
- goto fail;
- }
- for(vec=0;vec<num_funcs;vec++) {
- for(code=0;the_funcs[vec][code].func_name;code++)
- if(!stricmp(cmdstr,the_funcs[vec][code].func_name))
- goto fini;
- }
- for(code=0;code<num_maps;code++) {
- if(!strcmp(cmdstr,map_names[code])) {
- vec=255;
- goto fini;
- }
- }
- if(get_abs_rng(&cmdstr,&rng)) {
- error_msg("Unknown command '%s'",cmdstr);
- goto fail;
- }
-
- vec=bound_macro_vec;
- for(code=0;code<n_bound_macros;code++) {
- if(!bcmp(&bound_macros[code],&rng,sizeof(struct rng)))
- goto fini;
- }
-
- ptr=range_name(&rng);
- if(!bound_macro_vec) {
- bound_macros=ck_malloc(sizeof(struct rng));
- n_bound_macros=1;
- tmpfunc=ck_malloc(sizeof(struct cmd_func));
- bound_macro_vec=add_usr_cmds(tmpfunc);
- } else {
- n_bound_macros++;
-
- bound_macros=ck_realloc(bound_macros,n_bound_macros*sizeof(struct rng));
-
- the_funcs[bound_macro_vec]=ck_realloc(the_funcs[bound_macro_vec],n_bound_macros*sizeof(struct cmd_func));
- tmpfunc= &the_funcs[bound_macro_vec][n_bound_macros-1];
- }
- bound_macros[n_bound_macros-1]=rng;
- tmpfunc->func_args=ck_malloc(strlen(ptr)+5);
- tmpfunc->func_args[0]='n';
- tmpfunc->func_args[1]='a'+(n_bound_macros-1)/26;
- tmpfunc->func_args[2]='a'+(n_bound_macros-1)%26;
- tmpfunc->func_args[3]='\0';
- tmpfunc->func_name=tmpfunc->func_args+4;
- strcpy(tmpfunc->func_name,ptr);
- tmpfunc->func_flags=ALL;
- tmpfunc->func_func=bound_macro;
- fini:
- do_bind_key(the_maps[map],c,vec,code);
- fail:
- sprint_line(&in_line[16],"%s %s %s",text,cmdstr,char_to_string(c));
- }
-
- static void
- do_bind_key FUN4(struct keymap *,map, int,key, unsigned char,vector, unsigned char,code)
- {
- struct keymap *m;
- struct key *k;
- int n;
-
-
- for(m=map;m;m=m->map_next) {
- if(key+1>=m->lochr && key-1<=m->hichr)
- break;
- if(m->map_end)
- m=0;
- }
- if(m->map_dense) {
- if(vector==m->keys[0].vector && code==m->keys[0].code) {
- if(key<m->lochr)
- m->lochr=key;
- if(key>m->hichr)
- m->hichr=key;
- return;
- } else if(m->lochr!=m->hichr)
- m=0;
- else
- m->map_dense=0;
- }
- if(m==0) {
- m=ck_malloc(sizeof(struct keymap));
- *m= *map;
- map->map_next=m;
- m=map;
- m->map_end=0;
- m->map_dense=1;
- m->map_malloc=2;
- m->lochr=key;
- m->hichr=key;
- m->keys=ck_malloc(sizeof(struct key));
- }
- if(key<m->lochr) {
- n=sizeof(struct key)*(1+m->hichr-m->lochr);
- k=ck_malloc(n+sizeof(struct key));
- bcopy(&m->keys[0],&k[1],n);
- if(m->map_malloc==2)
- free(m->keys);
- m->keys=k;
- m->lochr=key;
- m->map_malloc=2;
- }
- if(key>m->hichr) {
- if(m->map_malloc==2)
- {
-
- m->keys=ck_realloc(m->keys,sizeof(struct key)*(1+m->hichr-m->lochr));
- }
- else {
- n=sizeof(struct key)*(1+m->hichr-m->lochr);
- k=ck_malloc(n+sizeof(struct key));
- bcopy(&m->keys[0],k,n);
- m->keys=k;
- m->map_malloc=2;
- }
- m->hichr=key;
- }
- if(!m->map_malloc) {
- n=sizeof(struct key)*(1+m->hichr-m->lochr);
- k=ck_malloc(n);
- bcopy(&m->keys[0],k,n);
- m->keys=k;
- m->map_malloc=2;
- }
- m->keys[key-m->lochr].vector=vector;
- m->keys[key-m->lochr].code=code;
- }
-
- static void
- interact_macro_cmd FUN0()
- {
- error_msg("Command not implemented");
- return;
- }
-
- static void
- kill_cell_cmd FUN0()
- {
- CELL *cp;
-
- cp=find_cell(curow,cucol);
- if(!cp)
- return;
- if((GET_LCK(cp)==LCK_DEF && default_lock==LCK_LCK) || GET_LCK(cp)==LCK_LCK) {
- error_msg("Cell %s is locked",cell_name(curow,cucol));
- return;
- }
- new_value(curow,cucol,"");
- cp->cell_flags=0;
- modified=1;
- }
-
- static void
- format_cell_cmd FUN0()
- {
- struct rng to;
-
- to.lr=to.hr=curow;
- to.lc=to.hc=cucol;
- format_area(&to);
- }
-
- static void
- kill_all_cmd FUN0()
- {
- clear_spreadsheet();
- disp_scrn();
- }
-
- #if 0
- static void
- do_ansi_cmd FUN0()
- {
- int c;
-
- c=get_chr();
- if(c>='A' && c<='D')
- shift_cell_cursor(c-'A');
- else
- /* ? ? ? */;
- }
- #endif
-
- static void
- do_input_cmd FUN2(int, n, int,c)
- {
- CELL *cp;
- char *fail;
-
- extern char *cell_value_string EXT2(CELLREF, CELLREF);
-
- switch(n) {
- /* Edit cell */
- case 0:
- if(cp=find_cell(curow,cucol)) {
- set_line(&val_line,decomp(curow,cucol,cp));
- decomp_free();
- } else
- set_line(&val_line,0);
- break;
-
- /* Edit Cell Value */
- case 1:
- set_line(&val_line,cell_value_string(curow,cucol));
- break;
-
- case 2: /* Set-cell */
- set_line(&val_line,"x");
- val_line.buf[0]=c;
- break;
-
- /* New Def Cell */
- case 3:
- break;
- #ifdef TEST
- default:
- panic("Unknown value in do_input_cell (%d)",n);
- #endif
- }
- cp=find_cell(curow,cucol);
- if(((!cp || GET_LCK(cp)==LCK_DEF) && default_lock==LCK_LCK) || (cp && GET_LCK(cp)==LCK_LCK)) {
- error_msg("Cell %s is locked",cell_name(curow,cucol));
- return;
- }
- setrow=curow;
- setcol=cucol;
- if(get_inp_line("set-cell",&val_line)>1)
- return;
- fail=new_value(setrow,setcol,val_line.buf);
- if(fail)
- error_msg(fail);
- else
- modified=1;
- }
-
- static void
- do_break_cmd FUN0()
- {
- if(mkrow!=NON_ROW) {
- mkrow=NON_ROW;
- how_many=1;
- cur_status();
- }
- }
-
- static void
- digit_cmd FUN1(int, magic)
- {
- struct keymap *map;
-
- for(map=the_maps[DIGIT_MAP];map->map_end==0;map=map->map_next)
- ;
- map->map_next= the_maps[magic];
- how_many=0;
- do {
- how_many=how_many * 10 + cur_cmd - &cmd_funcs[DIGIT_0];
- cur_status();
- map_chr(DIGIT_MAP);
- } while(cur_cmd>= &cmd_funcs[DIGIT_0] && cur_cmd<= &cmd_funcs[DIGIT_9]);
- }
-
-
-