This patch will add the following functions to eppic:

1) Allow main() as the entry for any eppic program. Previously only func()
   which companied by func_help() & func_usage() is regarded as the main
   entry of the eppic program. This constraint only makes sense for creating
   a crash-like cmd. If users only want to create a oneshot run program for
   fast testing, then the constraint is misleading. So this patch will add
   main() as entry for eppic programs.

2) Add new option "-r" for eppic cmd "edit". Previously eppic expect programs
   to run as the form of crash-like cmd, and it is not convenient for the
   oneshot run programs. Luckly the programs can be executed automatically
   after "edit -f". So I create a "edit -r" cmd to run the eppic program
   without invoke the editor, in order to reuse the code. So eppic programs
   can be now executed by "edit -r myfile.c", and "edit -r" will be alias as
   "eppic" in later patches, so a eppic program can be run simply by
   "eppic myfile.c".

3) Add a template for any new eppic program files. If "edit -f" a new file, a
   template with an example will be written into the new file. So users can
   refer to it when writting any eppic programs.

Signed-off-by: Tao Liu <l...@redhat.com>
---
 extensions/eppic.mk    |  13 ++-
 extensions/eppic.patch | 195 +++++++++++++++++++++++++++++++++++++++++
 2 files changed, 207 insertions(+), 1 deletion(-)
 create mode 100644 extensions/eppic.patch

diff --git a/extensions/eppic.mk b/extensions/eppic.mk
index 9435793..b175df5 100644
--- a/extensions/eppic.mk
+++ b/extensions/eppic.mk
@@ -53,7 +53,18 @@ all:
                        fi; \
                        if  [ -f $(APPFILE) ]; \
                        then \
-                               make -f eppic.mk eppic.so; \
+                               pushd eppic >/dev/null; \
+                               if patch --dry-run -N -p0 < ../eppic.patch 
>/dev/null ; then \
+                                       patch -N -p0 < ../eppic.patch; \
+                                       popd >/dev/null; \
+                                       make -f eppic.mk eppic.so; \
+                               elif patch --dry-run -N -p0 -R < ../eppic.patch 
>/dev/null ; then \
+                                       popd >/dev/null; \
+                                       make -f eppic.mk eppic.so; \
+                               else \
+                                       popd >/dev/null; \
+                                       echo "eppic.so: apply eppic.patch 
error"; \
+                               fi; \
                        else \
                                echo "eppic.so: failed to pull eppic code from 
git repo"; \
                        fi; \
diff --git a/extensions/eppic.patch b/extensions/eppic.patch
new file mode 100644
index 0000000..f38eac0
--- /dev/null
+++ b/extensions/eppic.patch
@@ -0,0 +1,195 @@
+--- applications/crash/eppic.c
++++ applications/crash/eppic.c
+@@ -642,12 +642,12 @@ FILE *ofp = NULL;
+               eppic_setofile(ofp);
+ }
+ 
+-
++void *eppic_findfile(char *, int);
+ void
+ edit_cmd(void)
+ {
+-int c, file=0;
+-        while ((c = getopt(argcnt, args, "lf")) != EOF) {
++int c, file=0, run=0;
++        while ((c = getopt(argcnt, args, "lfr")) != EOF) {
+                 switch(c)
+                 {
+                 case 'l':
+@@ -657,6 +657,9 @@ int c, file=0;
+                 case 'f':
+                     file++;
+                 break;
++                case 'r':
++                    run++;
++                break;
+                 default:
+                         argerrs++;
+                         break;
+@@ -666,10 +669,17 @@ int c, file=0;
+         if (argerrs)
+                 cmd_usage(crash_global_cmd(), SYNOPSIS);
+ 
+-        else if(args[optind]) {
++        else if(args[optind] && file && !run) {
+             while(args[optind]) {
+               eppic_vi(args[optind++], file);
+             }
++      } else if(args[optind] && !file && run) {
++            while(args[optind]) {
++              eppic_load(args[optind]);
++              if (eppic_findfile(args[optind], 0))
++                      eppic_unload(args[optind]);
++              optind++;
++            }
+       }
+         else cmd_usage(crash_global_cmd(), SYNOPSIS);
+ }
+@@ -677,7 +687,7 @@ int c, file=0;
+ char *edit_help[]={
+               "edit",
+                 "Start a $EDITOR session of a eppic function or file",
+-                "<-f fileName>|<function name>",
++                "<-f fileName>|<function name>|<-r fileName>",
+                 "This command can be use during a tight development cycle",
+                 "where frequent editing->run->editing sequences are 
executed.",
+                 "To edit a known eppic macro file use the -f option. To edit 
the file",
+@@ -689,6 +699,10 @@ char *edit_help[]={
+                 "  %s> edit ps",
+                 "  %s> edit ps_opt",
+                 "  %s> edit -l",
++              "Oneshot run from main():",
++                "  %s> edit -r myfile.c",
++              "Or:",
++                "  %s> eppic myfile.c",
+                 NULL
+ };
+ 
+@@ -885,6 +899,13 @@ char **help=malloc(sizeof *help * 5);
+         }
+     }
+     free(help);
++
++    if (load && !strcmp(name, "main")) {
++        int optind_save = optind;
++        eppic_cmd(name, NULL, 0);
++        optind = optind_save;
++    }
++
+     return;
+ }
+ 
+--- libeppic/eppic_func.c
++++ libeppic/eppic_func.c
+@@ -22,6 +22,8 @@
+ #include <sys/types.h>
+ #include <time.h>
+ #include <sys/stat.h>
++#include <fcntl.h>
++#include <unistd.h>
+ #include "eppic.h"
+ 
+ /*
+@@ -793,6 +795,37 @@ char *ed=getenv("EDITOR");
+     if(!system(buf)) eppic_load(fname);
+ }
+ 
++static const char *example[] = {
++"/*                                                                           
",
++" * Example: Output all PIDs by eppic program.                                
        ",
++" *                                                                           
",
++" * // Global variables and kernel data structures can be used directly.      
",
++" * // If any are within kernel modules, should preload the .ko first via     
",
++" * // \"mod -S/-s\" cmd in crash before invoke your eppic program.           
",
++" *                                                                           
",
++" * int main(void)                                                            
",
++" * {                                                                         
",
++" *     struct task_struct *p;                                                
        ",
++" *     unsigned long offset;                                                 
",
++" *                                                                           
",
++" *     p = (struct task_struct *)&init_task;                                 
",
++" *     offset = (unsigned long)&(p->tasks) - (unsigned long)p;               
",
++" *                                                                           
",
++" *     do {                                                                  
",
++" *         printf(\"PID: %d\\n\", (int)(p->pid));                            
",
++" *         p = (struct task_struct *)((unsigned long)(p->tasks.next) - 
offset);",
++" *     } while(p != &init_task);                                             
",
++" *                                                                           
",
++" *     return 0;                                                             
",
++" * }                                                                         
",
++" *                                                                           
",
++" * crash> eppic file_name.c                                                  
",
++" * or                                                                        
        ",
++" * crash> edit -r file_name.c                                                
        ",
++" */                                                                          
",
++};
++
++char *eppic_get_func_file(char *);
+ /*
+     This funciton is called to start a vi session on a function
+     (file=0) or a file (file=1);
+@@ -800,24 +833,31 @@ char *ed=getenv("EDITOR");
+ void
+ eppic_vi(char *fname, int file)
+ {
+-int line, freeit=0;
++int line=1, freeit=0, fd;
+ char *filename;
++char newline = '\n';
+ 
+     if(file) {
+ 
+         filename=eppic_filempath(fname);
+ 
+         if(!filename) {
+-
+-            eppic_msg("File not found : %s\n", fname);
+-            return;
+-
+-        }
+-
+-        line=1;
+-        freeit=1;
+-
+-
++          fd = creat(fname, 0644);
++          if (fd < 0) {
++              eppic_msg("File not found : %s\n", fname);
++              return;
++          } else {
++              for (int i = 0; i < sizeof(example)/sizeof(char *); i++) {
++                      write(fd, example[i], strlen(example[i]));
++                      write(fd, &newline, sizeof(newline));
++              }
++              close(fd);
++              filename = fname;
++              freeit=0;
++          }
++        } else {
++            freeit=1;
++      }
+     } else {
+ 
+         func *f=eppic_getfbyname(fname, 0);
+@@ -837,6 +877,10 @@ char *filename;
+ 
+     eppic_exevi(filename, line);
+ 
++    char *fi_name = eppic_get_func_file("main");
++    if (fi_name)
++        eppic_deletefile(fi_name);
++
+     if(freeit) eppic_free(filename);
+ 
+ }
+@@ -1184,3 +1228,10 @@ eppic_runcmd(char *fname, var_t*args)
+     return 0;
+ }
+ 
++char *eppic_get_func_file(char *funcname)
++{
++      func *fn = eppic_getfbyname(funcname, 0);
++      if (!fn)
++              return NULL;
++      return fn->file->fname;
++}
-- 
2.47.0
--
Crash-utility mailing list -- devel@lists.crash-utility.osci.io
To unsubscribe send an email to devel-le...@lists.crash-utility.osci.io
https://${domain_name}/admin/lists/devel.lists.crash-utility.osci.io/
Contribution Guidelines: https://github.com/crash-utility/crash/wiki

Reply via email to