176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman/* -*- c -*- ------------------------------------------------------------- * 276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * 376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * Copyright 2004-2005 Murali Krishnan Ganapathy - All Rights Reserved 476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * 576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * This program is free software; you can redistribute it and/or modify 676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * it under the terms of the GNU General Public License as published by 776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * the Free Software Foundation, Inc., 53 Temple Place Ste 330, 876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * Boston MA 02111-1307, USA; either version 2 of the License, or 976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * (at your option) any later version; incorporated herein by reference. 1076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * 1176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman * ----------------------------------------------------------------------- */ 1276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 1376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman#include "help.h" 1476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman#include <stdio.h> 1576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman#include "string.h" 1676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman#include "com32io.h" 1776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman#include <syslinux/loadfile.h> // to read entire file into memory 1876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 1976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanint nc, nr; // Number of columns/rows of the screen 2076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanchar helpbasedir[HELPDIRLEN]; // name of help directory limited to HELPDIRLEN 2176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 2276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman// Find the occurence of the count'th \n in buffer (or NULL) if not found 2376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanstatic char *findline(char *buffer, int count) 2476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 2576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman int ctr; 2676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char *p = buffer - 1; 2776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 2876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (count < 1) 2976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return buffer; 3076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman for (ctr = 0; ctr < count; ctr++) { 3176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman p = strchr(p + 1, '\n'); 3276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (p == NULL) 3376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return NULL; 3476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 3576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return p; 3676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 3776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 3876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman// return the number of lines in buffer 3976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanstatic int countlines(char *buffer) 4076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 4176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman int ans; 4276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman const char *p; 4376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 4476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman p = buffer - 1; 4576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman ans = 1; 4676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman while (p) { 4776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman p = strchr(p + 1, '\n'); 4876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman ans++; 4976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 5076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return ans; 5176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 5276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 5376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman// Print numlines of text starting from buf 5476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanstatic void printtext(char *buf, int from) 5576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 5676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char *f, *t; 5776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman int nlines, i; 5876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 5976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman // clear window to print 6076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman nlines = nr - HELP_BODY_ROW - HELP_BOTTOM_MARGIN - 1; 6176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 6276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman f = findline(buf, from); 6376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (!f) 6476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return; // nothing to print 6576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (*f == '\n') 6676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman f++; // start of from+1st line 6776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman t = f; 6876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 6976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman for (i = 0; i < nlines; i++) { 7076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(HELP_BODY_ROW + i, HELP_LEFT_MARGIN); 7176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman clear_end_of_line(); 7276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(SO); 7376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(HELP_BODY_ROW + i, nc - 1); 7476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putch(LEFT_BORDER, 0x07); 7576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(SI); 7676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 7776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(HELP_BODY_ROW + i, HELP_LEFT_MARGIN); 7876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman while (*t != '\n') { 7976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (*t == '\0') 8076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return; 8176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(*t); 8276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman t++; 8376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 8476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar('\n'); 8576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman t++; 8676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 8776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 8876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 8976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanvoid showhelp(const char *filename) 9076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 9176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char ph; 9276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char *title, *text; 9376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman union { 9476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char *buffer; 9576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman void *vbuf; 9676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } buf; // This is to avoild type-punning issues 9776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 9876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char line[512]; 9976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman size_t size; 10076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman int scan; 10176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman int rv, numlines, curr_line; 10276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 10376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (getscreensize(1, &nr, &nc)) { 10476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman /* Unknown screen size? */ 10576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman nc = 80; 10676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman nr = 24; 10776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 10876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman ph = nr - HELP_BODY_ROW; 10976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman cls(); 11076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 11176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman /* Turn autowrap off, to avoid scrolling the menu */ 11276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman printf(CSI "?7l"); 11376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 11476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (filename == NULL) { // print file contents 11576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman strcpy(line, "Filename not given"); 11676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman goto puke; 11776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 11876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 11976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman rv = loadfile(filename, (void **)&buf.vbuf, &size); // load entire file into memory 12076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (rv < 0) { // Error reading file or no such file 12176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman sprintf(line, "Error reading file or file not found\n file=%s", filename); 12276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman goto puke; 12376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 12476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 12576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman title = buf.buffer; 12676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman text = findline(title, 1); // end of first line 12776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman *text++ = '\0'; // end the title string and increment text 12876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 12976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman // Now we have a file just print it. 13076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman numlines = countlines(text); 13176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line = 0; 13276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman scan = KEY_ESC + 1; // anything except ESCAPE 13376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 13476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman /* top, left, bottom, right, attr */ 13576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman drawbox(0, 0, nr - 1, nc - 1, 0x07); 13676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman while (scan != KEY_ESC) { 13776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman /* Title */ 13876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(1, (nc - strlen(title)) / 2); 13976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman fputs(title, stdout); 14076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman drawhorizline(2, HELP_LEFT_MARGIN - 1, nc - HELP_RIGHT_MARGIN, 0x07, 0); // dumb==0 14176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman /* Text */ 14276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman printtext(text, curr_line); 14376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(HELP_BODY_ROW - 1, nc - HELP_RIGHT_MARGIN); 14476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (curr_line > 0) 14576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(HELP_MORE_ABOVE); 14676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman else 14776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(' '); 14876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(nr - HELP_BOTTOM_MARGIN - 1, nc - HELP_RIGHT_MARGIN); 14976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (curr_line < numlines - ph) 15076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(HELP_MORE_BELOW); 15176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman else 15276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman putchar(' '); 15376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 15476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman scan = get_key(stdout, 0); // wait for user keypress 15576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 15676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman switch (scan) { 15776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman case KEY_HOME: 15876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line = 0; 15976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 16076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman case KEY_END: 16176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line = numlines; 16276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 16376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman case KEY_UP: 16476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line--; 16576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 16676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman case KEY_DOWN: 16776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line++; 16876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 16976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman case KEY_PGUP: 17076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line -= ph; 17176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 17276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman case KEY_PGDN: 17376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line += ph; 17476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 17576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman default: 17676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 17776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 17876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (curr_line > numlines - ph) 17976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line = numlines - ph; 18076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (curr_line < 0) 18176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman curr_line = 0; 18276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 18376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanout: 18476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman cls(); 18576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman return; 18676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 18776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanpuke: 18876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman gotoxy(HELP_BODY_ROW, HELP_LEFT_MARGIN); 18976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman fputs(line, stdout); 19076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman while (1) { 19176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman scan = get_key(stdin, 0); 19276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (scan == KEY_ESC) 19376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman break; 19476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } 19576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman goto out; 19676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 19776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 19876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanvoid runhelp(const char *filename) 19976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 20076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char fullname[HELPDIRLEN + 16]; 20176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 20276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman cls(); 20376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman cursoroff(); 20476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (helpbasedir[0] != 0) { 20576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman strcpy(fullname, helpbasedir); 20676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman strcat(fullname, "/"); 20776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman strcat(fullname, filename); 20876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman showhelp(fullname); 20976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman } else 21076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman showhelp(filename); // Assume filename is absolute 21176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 21276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 21376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanvoid runhelpsystem(unsigned int helpid) 21476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 21576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman char filename[15]; 21676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 21776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman sprintf(filename, "hlp%05d.txt", helpid); 21876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman runhelp(filename); 21976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 22076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 22176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanvoid init_help(const char *helpdir) 22276d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 22376d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman if (helpdir != NULL) 22476d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman strcpy(helpbasedir, helpdir); 22576d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman else 22676d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman helpbasedir[0] = 0; 22776d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 22876d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman 22976d05dc695b06c4e987bb8078f78032441e1430cGreg Hartmanvoid close_help(void) 23076d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman{ 23176d05dc695b06c4e987bb8078f78032441e1430cGreg Hartman} 232