Here is an updated diff with following changes...

Manpage update.
Remove conditional compilation of cscope functionality.
Fixed a memory leak in csexists function.
Treat current word at cursor as default input for cscope commands.

Comments?

Index: Makefile
===================================================================
RCS file: /cvs/src/usr.bin/mg/Makefile,v
retrieving revision 1.25
diff -u -p -r1.25 Makefile
--- Makefile    28 Nov 2011 04:41:39 -0000      1.25
+++ Makefile    14 May 2012 17:43:32 -0000
@@ -24,7 +24,7 @@ SRCS= autoexec.c basic.c buffer.c cinfo.
 #
 # More or less standalone extensions.
 #
-SRCS+= cmode.c dired.c grep.c tags.c theo.c
+SRCS+= cmode.c cscope.c dired.c grep.c tags.c theo.c
 
 afterinstall:
        ${INSTALL} -d ${DESTDIR}${DOCDIR}/mg
Index: README
===================================================================
RCS file: /cvs/src/usr.bin/mg/README,v
retrieving revision 1.8
diff -u -p -r1.8 README
--- README      1 Aug 2011 12:15:23 -0000       1.8
+++ README      14 May 2012 17:40:21 -0000
@@ -63,6 +63,12 @@ bytes.
 
 
 
+While navigating source code using Mg's cscope commands, the cursor
+is always at the match location rather than in *cscope* buffer. Mg uses
+the same keybindings of GNU Emacs's xcscope package for it's cscope commands.
+As Mg's keybindings are case-insensitive some of the commands don't have a
+default keybinding.
+
 New implementation oddities:
 
 insert and define-key are new commands corresponding to the mocklisp
Index: cscope.c
===================================================================
RCS file: cscope.c
diff -N cscope.c
--- /dev/null   1 Jan 1970 00:00:00 -0000
+++ cscope.c    30 May 2012 16:41:25 -0000
@@ -0,0 +1,612 @@
+/*
+ * Copyright (c) 2012 Sunil Nimmagadda <su...@sunilnimmagadda.com>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <sys/queue.h>
+
+#include <ctype.h>
+#include <fcntl.h>
+#include <fnmatch.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "def.h"
+
+#define CSSYMBOL      0
+#define CSDEFINITION  1
+#define CSCALLEDFUNCS 2
+#define CSCALLERFUNCS 3
+#define CSTEXT        4
+#define CSEGREP       6
+#define CSFINDFILE    7
+#define CSINCLUDES    8
+
+struct cstokens {
+       const char *fname;
+       const char *function;
+       const char *lineno;
+       const char *pattern;
+};
+
+struct csmatch {
+       TAILQ_ENTRY(csmatch) entry;
+       int lineno;
+};
+
+struct csrecord {
+       TAILQ_ENTRY(csrecord) entry;
+       char *filename;
+       TAILQ_HEAD(matches, csmatch) matches;
+};
+
+static TAILQ_HEAD(csrecords, csrecord) csrecords = 
TAILQ_HEAD_INITIALIZER(csrecords);
+static struct csrecord *addentryr;
+static struct csrecord *currecord;
+static struct csmatch  *curmatch;
+static const char      *addentryfn;
+static const char      *csprompt[] = {
+       "Find this symbol: ",
+       "Find this global definition: ",
+       "Find functions called by this function: ",
+       "Find functions calling this function: ",
+       "Find this text string: ",
+       "Change this text string: ",
+       "Find this egrep pattern: ",
+       "Find this file: ",
+       "Find files #including this file: "
+};
+
+static int  addentry(struct buffer *, char *);
+static void csflush(void);
+static int  do_cscope(int);
+static int  csexists(const char *);
+static int  getattr(char *, struct cstokens *);
+static int  jumptomatch(void);
+static void prettyprint(struct buffer *, struct cstokens *);
+static const char *ltrim(const char *);
+
+/*
+ * Find this symbol. Bound to C-c s s
+ */
+/* ARGSUSED */
+int
+cssymbol(int f, int n)
+{
+       return (do_cscope(CSSYMBOL));
+}
+
+/*
+ * Find this global definition. Bound to C-c s d
+ */
+/* ARGSUSED */int
+csdefinition(int f, int n)
+{
+       return (do_cscope(CSDEFINITION));
+}
+
+/*
+ * Find functions called by this function. Bound to C-c s l
+ */
+/* ARGSUSED */
+int
+csfuncalled(int f, int n)
+{
+       return (do_cscope(CSCALLEDFUNCS));
+}
+
+/*
+ * Find functions calling this function. Bound to C-c s c
+ */
+/* ARGSUSED */
+int
+cscallerfuncs(int f, int n)
+{
+       return (do_cscope(CSCALLERFUNCS));
+}
+
+/*
+ * Find this text. Bound to C-c s t
+ */
+/* ARGSUSED */
+int
+csfindtext(int f, int n)
+{
+       return (do_cscope(CSTEXT));
+}
+
+/*
+ * Find this egrep pattern. Bound to C-c s e
+ */
+/* ARGSUSED */
+int
+csegrep(int f, int n)
+{
+       return (do_cscope(CSEGREP));
+}
+
+/*
+ * Find this file. Bound to C-c s f
+ */
+/* ARGSUSED */
+int
+csfindfile(int f, int n)
+{
+       return (do_cscope(CSFINDFILE));
+}
+
+/*
+ * Find files #including this file. Bound to C-c s i
+ */
+/* ARGSUSED */
+int
+csfindinc(int f, int n)
+{
+       return (do_cscope(CSINCLUDES));
+}
+
+/*
+ * Create list of files to index in the given directory
+ * using cscope-indexer.
+ */
+/* ARGSUSED */
+int
+cscreatelist(int f, int n)
+{
+       struct buffer *bp;
+       struct stat sb;
+       FILE *fpipe;
+       char dir[NFILEN], cmd[BUFSIZ], title[BUFSIZ], *line, *bufp;
+       size_t len;
+       int clen;
+       
+       if (getbufcwd(dir, sizeof(dir)) == FALSE)
+               dir[0] = '\0';
+       
+       bufp = eread("Index files in directory: ", dir, 
+           sizeof(dir), EFCR | EFDEF | EFNEW | EFNUL);
+       
+       if (bufp == NULL)
+               return (ABORT);
+       else if (bufp[0] == '\0')
+               return (FALSE);
+               
+       if (stat(dir, &sb) == -1) {
+               ewprintf("stat: %s", strerror(errno));
+               return (FALSE);
+       } else if (S_ISDIR(sb.st_mode) == 0) {
+               ewprintf("%s: Not a directory", dir);
+               return (FALSE);
+       }
+       
+       if (csexists("cscope-indexer") == FALSE) {
+               ewprintf("no such file or directory, cscope-indexer");
+               return (FALSE);
+       }
+       
+       clen = snprintf(cmd, sizeof(cmd), "cscope-indexer -v %s", dir);
+       if (clen < 0 || clen >= sizeof(cmd))
+               return (FALSE);
+
+       if ((fpipe = popen(cmd, "r")) == NULL) {
+               ewprintf("problem opening pipe");
+               return (FALSE);
+       }
+       
+       bp = bfind("*cscope*", TRUE);
+       if (bclear(bp) != TRUE)
+               return (FALSE);
+       bp->b_flag |= BFREADONLY;
+
+       clen = snprintf(title, sizeof(title), "%s%s",
+           "Creating cscope file list 'cscope.files' in: ", dir);
+       if (clen < 0 || clen >= sizeof(title))
+               return (FALSE);
+       addline(bp, title);
+       addline(bp, "");
+       /* All lines are NUL terminated */
+       while ((line = fgetln(fpipe, &len)) != NULL) {
+               line[len - 1] = '\0';
+               addline(bp, line);
+       }
+       pclose(fpipe);
+       return (popbuftop(bp, WNONE));  
+}
+
+/*
+ * Next Symbol. Bound to C-c s n
+ */
+/* ARGSUSED */
+int
+csnextmatch(int f, int n)
+{
+       struct csrecord *r;
+       struct csmatch *m;
+       
+       if (curmatch == NULL) {
+               if ((r = TAILQ_FIRST(&csrecords)) == NULL) {
+                       ewprintf("The *cscope* buffer does not exist yet");
+                       return (FALSE);
+               }
+               currecord = r;
+               curmatch = TAILQ_FIRST(&r->matches);
+       } else {
+               m = TAILQ_NEXT(curmatch, entry);
+               if (m == NULL) {
+                       r = TAILQ_NEXT(currecord, entry);
+                       if (r == NULL) {
+                               ewprintf("The end of *cscope* buffer has been 
reached");
+                               return (FALSE);
+                       } else {
+                               currecord = r;
+                               curmatch = TAILQ_FIRST(&currecord->matches);
+                       }
+               } else
+                       curmatch = m;
+       }
+       return (jumptomatch());
+}
+
+/*
+ * Previous Symbol. Bound to C-c s p
+ */
+/* ARGSUSED */
+int
+csprevmatch(int f, int n)
+{
+       struct csmatch *m;
+       struct csrecord *r;
+
+       if (curmatch == NULL)
+               return (FALSE);
+       else {
+               m  = TAILQ_PREV(curmatch, matches, entry);
+               if (m)
+                       curmatch = m;
+               else {
+                       r = TAILQ_PREV(currecord, csrecords, entry);
+                       if (r == NULL) {
+                               ewprintf("The beginning of *cscope* buffer has 
been reached");
+                               return (FALSE);
+                       } else {
+                               currecord = r;
+                               curmatch = TAILQ_LAST(&currecord->matches, 
matches);
+                       }
+               }
+       }
+       return (jumptomatch());
+}
+
+/*
+ * Next file.
+ */
+int
+csnextfile(int f, int n)
+{
+       struct csrecord *r;
+       
+       if (curmatch == NULL) {
+               if ((r = TAILQ_FIRST(&csrecords)) == NULL) {
+                       ewprintf("The *cscope* buffer does not exist yet");
+                       return (FALSE);
+               }
+
+       } else {
+               if ((r = TAILQ_NEXT(currecord, entry)) == NULL) {
+                       ewprintf("The end of *cscope* buffer has been reached");
+                       return (FALSE);
+               }
+       }
+       currecord = r;
+       curmatch = TAILQ_FIRST(&currecord->matches);
+       return (jumptomatch()); 
+}
+
+/*
+ * Previous file.
+ */
+int
+csprevfile(int f, int n)
+{
+       struct csrecord *r;
+       
+       if (curmatch == NULL) {
+               if ((r = TAILQ_FIRST(&csrecords)) == NULL) {
+                       ewprintf("The *cscope* buffer does not exist yet");
+                       return (FALSE);
+               }
+
+       } else {
+               if ((r = TAILQ_PREV(currecord, csrecords, entry)) == NULL) {
+                       ewprintf("The beginning of *cscope* buffer has been 
reached");
+                       return (FALSE);
+               }
+       }
+       currecord = r;
+       curmatch = TAILQ_FIRST(&currecord->matches);
+       return (jumptomatch()); 
+}
+
+/*
+ * The current symbol location is extracted from currecord->filename and 
+ * curmatch->lineno. Load the file similar to filevisit and goto the 
+ * lineno recorded.
+ */
+int
+jumptomatch(void)
+{
+       struct buffer *bp;
+       char *adjf;
+       
+       if (curmatch == NULL || currecord == NULL)
+               return (FALSE);
+       adjf = adjustname(currecord->filename, TRUE);
+       if (adjf == NULL)
+               return (FALSE);
+       if ((bp = findbuffer(adjf)) == NULL)
+               return (FALSE);
+       curbp = bp;
+       if (showbuffer(bp, curwp, WFFULL) != TRUE)
+               return (FALSE);
+       if (bp->b_fname[0] == '\0') {
+               if (readin(adjf) != TRUE)
+                       killbuffer(bp);
+       }
+       gotoline(FFARG, curmatch->lineno);
+       return (TRUE);
+       
+}
+
+/*
+ * Ask for the symbol, construct cscope commandline with the symbol
+ * and passed in index. Popen cscope, read the output into *cscope* 
+ * buffer and pop it.
+ */
+int
+do_cscope(int i)
+{
+       struct buffer *bp;
+       FILE *fpipe;
+       char pattern[MAX_TOKEN], cmd[BUFSIZ], title[BUFSIZ];
+       char *p, *buf;
+       int clen, nores = 0;
+       size_t len;
+
+       /* If current buffer isn't a source file just return */
+       if (fnmatch("*.[chy]", curbp->b_fname, 0) != 0) {
+               ewprintf("C-c s not defined");
+               return (FALSE);
+       }
+       
+       if (curtoken(0, 1, pattern) == FALSE)
+               return (FALSE); 
+       p = eread(csprompt[i], pattern, MAX_TOKEN, EFNEW | EFCR | EFDEF);       
        
+       if (p == NULL)
+               return (ABORT);
+       else if (p[0] == '\0')
+               return (FALSE);
+
+       if (csexists("cscope") == FALSE) {
+               ewprintf("no such file or directory, cscope");
+               return (FALSE);
+       }
+       
+       csflush();
+       clen = snprintf(cmd, sizeof(cmd), "cscope -L -%d %s 2>/dev/null", i, 
pattern);
+       if (clen < 0 || clen >= sizeof(cmd))
+               return (FALSE);
+
+       if ((fpipe = popen(cmd, "r")) == NULL) {
+               ewprintf("problem opening pipe");
+               return (FALSE);
+       }
+       
+       bp = bfind("*cscope*", TRUE);
+       if (bclear(bp) != TRUE)
+               return (FALSE);
+       bp->b_flag |= BFREADONLY;
+
+       clen = snprintf(title, sizeof(title), "%s%s", csprompt[i], pattern);
+       if (clen < 0 || clen >= sizeof(title))
+               return (FALSE);
+       addline(bp, title);
+       addline(bp, "");
+       addline(bp, 
"-------------------------------------------------------------------------------");
+       /* All lines are NUL terminated */
+       while ((buf = fgetln(fpipe, &len)) != NULL) {
+               buf[len - 1] = '\0';
+               if (addentry(bp, buf) != TRUE)
+                       return (FALSE);
+               nores = 1;
+       }; 
+       pclose(fpipe);
+       addline(bp, 
"-------------------------------------------------------------------------------");
+       if (nores == 0)
+               ewprintf("No matches were found.");
+       return (popbuftop(bp, WNONE));
+}
+
+/*
+ * For each line read from cscope output, extract the tokens,
+ * add them to list and pretty print a line in *cscope* buffer.
+ */
+int
+addentry(struct buffer *bp, char *csline)
+{
+       struct csrecord *r;
+       struct csmatch *m;
+       struct cstokens t;
+       int lineno;
+       char buf[BUFSIZ];
+       const char *errstr;
+
+       r = NULL;
+       if (getattr(csline, &t) == FALSE)
+               return (FALSE);
+
+       lineno = strtonum(t.lineno, INT_MIN, INT_MAX, &errstr);
+       if (errstr)
+               return (FALSE);
+               
+       if (addentryfn == NULL || strcmp(addentryfn, t.fname) != 0) {
+               if ((r = malloc(sizeof(struct csrecord))) == NULL)
+                       goto cleanup;
+               addentryr = r;
+               if ((r->filename = strndup(t.fname, NFILEN)) == NULL)
+                       return (FALSE);
+               addentryfn = r->filename;
+               TAILQ_INIT(&r->matches);
+               if ((m = malloc(sizeof(struct csmatch))) == NULL)
+                       goto cleanup;
+               m->lineno = lineno;
+               TAILQ_INSERT_TAIL(&r->matches, m, entry);
+               TAILQ_INSERT_TAIL(&csrecords, r, entry);
+               addline(bp, "");
+               if (snprintf(buf, sizeof(buf), "*** %s", t.fname) < 0)
+                       goto cleanup;
+               addline(bp, buf);
+       } else {
+               if ((m = malloc(sizeof(struct csmatch))) == NULL)
+                       goto cleanup;
+               m->lineno = lineno;
+               TAILQ_INSERT_TAIL(&addentryr->matches, m, entry);
+       }
+       prettyprint(bp, &t);
+       return (TRUE);
+cleanup:
+       free(r);
+       return (FALSE);
+}
+
+/*
+ * Cscope line: <filename> <function> <lineno> <pattern>
+ */
+int
+getattr(char *line, struct cstokens *t)
+{
+       char *p;
+
+       if ((p = strchr(line, ' ')) == NULL)
+               return (FALSE);
+       *p++ = '\0';
+       t->fname = line;
+       line = p;
+
+       if ((p = strchr(line, ' ')) == NULL)
+               return (FALSE);
+       *p++ = '\0';
+       t->function = line;
+       line = p;
+
+       if ((p = strchr(line, ' ')) == NULL)
+               return (FALSE);
+       *p++ = '\0';
+       t->lineno = line;
+
+       if (*p == '\0')
+               return (FALSE);
+       t->pattern = p;
+
+       return (TRUE);
+}
+
+void
+prettyprint(struct buffer *bp, struct cstokens *t)
+{
+       char buf[BUFSIZ];
+
+       if (snprintf(buf, sizeof(buf), "%s[%s]\t\t%s",
+           t->function, t->lineno, ltrim(t->pattern)) < 0)
+               return;
+       addline(bp, buf);
+}
+
+const char *
+ltrim(const char *s)
+{
+       while (isblank(*s))
+               s++;
+       return s;
+}
+
+void
+csflush(void)
+{
+       struct csrecord *r;
+       struct csmatch *m;
+       
+       while ((r = TAILQ_FIRST(&csrecords)) != NULL) {
+               free(r->filename);
+               while ((m = TAILQ_FIRST(&r->matches)) != NULL) {
+                       TAILQ_REMOVE(&r->matches, m, entry);
+                       free(m);
+               }
+               TAILQ_REMOVE(&csrecords, r, entry);
+               free(r);
+       }
+       addentryr = NULL;
+       addentryfn = NULL;
+       currecord = NULL;
+       curmatch = NULL;
+}
+
+/*
+ * Check if the cmd exists in $PATH. Split on ":" and iterate through
+ * all paths in $PATH.
+ */
+int
+csexists(const char *cmd)
+{
+       char fname[MAXPATHLEN], *dir, *path, *pathc, *tmp;
+       int  cmdlen, dlen;
+
+       /* Special case if prog contains '/' */
+       if (strchr(cmd, '/')) {
+               if (access(cmd, F_OK) == -1)
+                       return (FALSE);
+               else
+                       return (TRUE);
+       }
+       if ((tmp = getenv("PATH")) == NULL)
+               return (FALSE);
+       if ((pathc = path = strdup(tmp)) == NULL) {
+               ewprintf("out of memory");
+               return (FALSE);
+       }
+       cmdlen = strlen(cmd);
+       while ((dir = strsep(&path, ":")) != NULL) {
+               if (*dir == '\0')
+                       *dir = '.';
+
+               dlen = strlen(dir);
+               while (dir[dlen-1] == '/')
+                       dir[--dlen] = '\0';     /* strip trailing '/' */
+
+               if (dlen + 1 + cmdlen >= sizeof(fname))  {
+                       ewprintf("path too long");
+                       goto cleanup;
+               }
+               snprintf(fname, sizeof(fname), "%s/%s", dir, cmd);
+               if(access(fname, F_OK) == 0) {
+                      free(pathc);
+                      return (TRUE);
+              }
+       }
+cleanup:
+       free(pathc);
+       return (FALSE);
+}
Index: def.h
===================================================================
RCS file: /cvs/src/usr.bin/mg/def.h,v
retrieving revision 1.118
diff -u -p -r1.118 def.h
--- def.h       10 Dec 2011 14:09:48 -0000      1.118
+++ def.h       30 May 2012 17:19:49 -0000
@@ -109,6 +109,8 @@ typedef int (*PF)(int, int);        /* generall
 #define KBACK  0x02            /* Backwards insert into kill ring */
 #define KREG   0x04            /* This is a region-based kill */
 
+#define MAX_TOKEN 64
+
 /*
  * This structure holds the starting position
  * (as a line/offset pair) and the number of characters in a
@@ -519,6 +521,22 @@ int                 joinline(int, int);
 int             findtag(int, int);
 int             poptag(int, int);
 int             tagsvisit(int, int);
+int             curtoken(int, int, char *);
+
+/* cscope.c */
+int            cssymbol(int, int);
+int            csdefinition(int, int);
+int            csfuncalled(int, int);
+int            cscallerfuncs(int, int);
+int            csfindtext(int, int);
+int            csegrep(int, int);
+int            csfindfile(int, int);
+int            csfindinc(int, int);
+int            csnextfile(int, int);
+int            csnextmatch(int, int);
+int            csprevfile(int, int);
+int            csprevmatch(int, int);
+int            cscreatelist(int, int);
 
 /* extend.c X */
 int             insert(int, int);
Index: funmap.c
===================================================================
RCS file: /cvs/src/usr.bin/mg/funmap.c,v
retrieving revision 1.35
diff -u -p -r1.35 funmap.c
--- funmap.c    28 Nov 2011 04:41:39 -0000      1.35
+++ funmap.c    14 May 2012 17:53:33 -0000
@@ -196,6 +196,19 @@ static struct funmap functnames[] = {
        {showcpos, "what-cursor-position",},
        {filewrite, "write-file",},
        {yank, "yank",},
+       {cssymbol, "cscope-find-this-symbol",},
+       {csdefinition, "cscope-find-global-definition",},
+       {csfuncalled, "cscope-find-called-functions",},
+       {cscallerfuncs, "cscope-find-functions-calling-this-function",},
+       {csfindtext, "cscope-find-this-text-string",},
+       {csegrep, "cscope-find-egrep-pattern",},
+       {csfindfile, "cscope-find-this-file",},
+       {csfindinc, "cscope-find-files-including-file",},
+       {csnextmatch, "cscope-next-symbol",},
+       {csprevmatch, "cscope-prev-symbol",},
+       {csnextfile, "cscope-next-file",},
+       {csprevfile, "cscope-prev-file",},
+       {cscreatelist, "cscope-create-list-of-files-to-index"},
        {NULL, NULL,}
 };
 
Index: keymap.c
===================================================================
RCS file: /cvs/src/usr.bin/mg/keymap.c,v
retrieving revision 1.46
diff -u -p -r1.46 keymap.c
--- keymap.c    28 Nov 2011 04:41:39 -0000      1.46
+++ keymap.c    14 May 2012 17:52:21 -0000
@@ -41,17 +41,55 @@ struct KEYMAPE (2 + IMAPEXT) helpmap = {
 };
 #endif /* !NO_HELP */
 
-struct KEYMAPE (1 + IMAPEXT) ccmap = {
+static PF cCsc[] = {
+       cscallerfuncs,          /* c */
+       csdefinition,           /* d */
+       csegrep,                /* e */
+       csfindfile,             /* f */
+       rescan,                 /* g */
+       rescan,                 /* h */
+       csfindinc,              /* i */
+       rescan,                 /* j */
+       rescan,                 /* k */
+       rescan,                 /* l */
+       rescan,                 /* m */
+       csnextmatch,            /* n */
+       rescan,                 /* o */
+       csprevmatch,            /* p */
+       rescan,                 /* q */
+       rescan,                 /* r */ 
+       cssymbol,               /* s */
+       csfindtext              /* t */
+};
+
+static struct KEYMAPE (1 + IMAPEXT) cCsmap = {
        1,
        1 + IMAPEXT,
        rescan,
        {
                {
-                       CCHR('@'), CCHR('@'), (PF[]){ rescan }, NULL
+                       'c', 't', cCsc, NULL
                }
        }
 };
 
+static PF cCs[] = {
+       NULL                    /* s */
+};
+
+struct KEYMAPE (2 + IMAPEXT) ccmap = {
+       2,
+       2 + IMAPEXT,
+       rescan,
+       {
+               {
+                       CCHR('@'), CCHR('@'), (PF[]){ rescan }, NULL
+               },
+               {
+                       's', 's', cCs, (KEYMAP *) & cCsmap
+               }
+       }
+};
 
 static PF cX4cF[] = {
        poptofile,              /* ^f */
Index: mg.1
===================================================================
RCS file: /cvs/src/usr.bin/mg/mg.1,v
retrieving revision 1.58
diff -u -p -r1.58 mg.1
--- mg.1        9 Feb 2012 09:00:14 -0000       1.58
+++ mg.1        14 May 2012 17:36:38 -0000
@@ -79,6 +79,13 @@ supports tag files created by
 .Xr ctags 1 ,
 allowing the user to quickly locate various object definitions.
 Note though that emacs uses etags, not ctags.
+.Sh CSCOPE
+.Nm
+supports navigating source code using cscope. However,
+.Nm
+requires cscope and cscope-indexer executables to be present in
+.Ev PATH
+for it to work.
 .Sh DEFAULT KEY BINDINGS
 Normal editing commands are very similar to GNU Emacs.
 In the following examples, C-x means Control-x, and M-x means Meta-x,
@@ -92,6 +99,24 @@ set-mark-command
 beginning-of-line
 .It C-b
 backward-char
+.It C-c s c
+cscope-find-functions-calling-this-function
+.It C-c s d
+cscope-find-global-definition
+.It C-c s e
+cscope-find-egrep-pattern
+.It C-c s f
+cscope-find-this-file
+.It C-c s i
+cscope-find-files-including-file
+.It C-c s n
+cscope-next-symbol
+.It C-c s p
+cscope-prev-symbol
+.It C-c s s
+cscope-find-this-symbol
+.It C-c s t
+cscope-find-this-text-string
 .It C-d
 delete-char
 .It C-e
@@ -365,6 +390,32 @@ This is a bit like a kill-region followe
 Count the number of lines matching the supplied regular expression.
 .It count-non-matches
 Count the number of lines not matching the supplied regular expression.
+.It cscope-find-this-symbol
+List the matches for the given symbol.
+.It cscope-find-global-definition
+List global definitions for the given literal.
+.It cscope-find-called-functions
+List functions called from the given function.
+.It cscope-find-functions-calling-this-function
+List functions calling the given function.
+.It cscope-find-this-text-string
+List locations matching the given text string.
+.It cscope-find-egrep-pattern
+List locations matching the given egrep pattern.
+.It cscope-find-this-file
+List filenames matching the given filename.
+.It cscope-find-files-including-file
+List files that #include the given filename.
+.It cscope-next-symbol
+Navigate to the next match.
+.It cscope-prev-symbol
+Navigate to the previous match.
+.It cscope-next-file
+Nagivate to the next file.
+.It cscope-prev-file
+Navigate to the previous file.
+.It cscope-create-list-of-files-to-index
+Create cscope's List and Index in the given directory.
 .It define-key
 Prompts the user for a named keymap (mode),
 a key, and an
Index: tags.c
===================================================================
RCS file: /cvs/src/usr.bin/mg/tags.c,v
retrieving revision 1.2
diff -u -p -r1.2 tags.c
--- tags.c      5 Dec 2011 07:17:02 -0000       1.2
+++ tags.c      29 May 2012 17:42:10 -0000
@@ -33,7 +33,6 @@ static int               addctag(char *)
 static int               atbow(void);
 void                     closetags(void);
 static int               ctagcmp(struct ctag *, struct ctag *);
-static int               curtoken(int, int, char *);
 static int               loadbuffer(char *);
 static int               loadtags(const char *);
 static int               pushtag(char *);
@@ -42,7 +41,6 @@ static struct ctag       *searchtag(char
 static char              *strip(char *, size_t);
 static void              unloadtags(void);
 
-#define MAX_TOKEN 64
 #define DEFAULTFN "tags"
 
 char *tagsfn = NULL;

Reply via email to