0001 
0002 
0003 
0004 
0005 
0006 
0007 
0008 
0009 
0010 
0011 
0012 
0013 
0014 
0015 
0016 
0017 
0018 
0019 
0020 
0021 
0022 
0023 
0024 
0025 
0026 
0027 
0028 
0029 
0030 
0031 
0032 
0033 
0034 
0035 
0036 #include <stdio.h>
0037 #include <stdlib.h>
0038 #include <time.h>
0039 
0040 #include <unistd.h>
0041 #include <stdarg.h>
0042 #include <ctype.h>
0043 #include <memory.h>
0044 #include <errno.h>
0045 #include <signal.h>
0046 #include <limits.h>
0047 #include <pthread.h>
0048 #include <string.h>
0049 #include <dirent.h>
0050 
0051 #include <ndrstandard.h>
0052 #include <ndebug.h>
0053 #include <nstdutil.h>
0054 #include <limits.h>
0055 #include <exhash.h>
0056 #include <sys_unix.h>
0057 
0058 #include <utlist.h>
0059 #include <pwd.h>
0060 #include <regex.h>
0061 
0062 #include "userlog.h"
0063 #include "exregex.h"
0064 #include "exparson.h"
0065 #include "atmi_int.h"
0066 
0067 
0068 
0069 
0070 
0071     
0072 
0073 
0074 #define MAX_ATFORKS         3
0075 
0076 
0077 
0078 
0079 
0080 
0081 #if defined(EX_OS_AIX) || defined(EX_OS_SUNOS)
0082 #define USE_STOCK_FORKING
0083 #endif
0084 
0085 
0086 
0087 
0088 
0089 
0090 
0091 
0092 
0093 exprivate void (*M_prepare[MAX_ATFORKS])(void) = {NULL, NULL, NULL}; 
0094 
0095 exprivate void (*M_parent[MAX_ATFORKS])(void) = {NULL, NULL, NULL};
0096 
0097 exprivate void (*M_child[MAX_ATFORKS])(void) = {NULL, NULL, NULL};
0098 
0099 
0100 
0101 
0102 
0103 
0104 
0105 
0106 
0107 
0108 expublic  string_hash_t * ndrx_string_hash_add_cnt(string_hash_t **h, char *str)
0109 {
0110 
0111     string_hash_t *el=NULL;
0112     
0113     el = ndrx_string_hash_get(*h, str);
0114     
0115     if (NULL!=el)
0116     {
0117         el->cnt++;
0118     }
0119     else
0120     {
0121         el = ndrx_string_hash_add(h, str);
0122         if (NULL!=el)
0123         {
0124             el->cnt=1;
0125         }
0126     }
0127     
0128     return el;
0129 }
0130 
0131 
0132 
0133 
0134 
0135 
0136 
0137 expublic string_hash_t * ndrx_string_hash_add(string_hash_t **h, char *str)
0138 {
0139     int ret = EXSUCCEED;
0140     string_hash_t * tmp = NDRX_CALLOC(1, sizeof(string_hash_t));
0141     
0142     if (NULL==tmp)
0143     {
0144 #ifdef SYSCOMMON_ENABLE_DEBUG
0145         NDRX_LOG(log_error, "alloc of string_hash_t (%d) failed", 
0146                 sizeof(string_hash_t));
0147 #endif
0148         EXFAIL_OUT(ret);
0149     }
0150 
0151     if (NULL==(tmp->str = strdup(str)))
0152     {
0153 #ifdef SYSCOMMON_ENABLE_DEBUG
0154         NDRX_LOG(log_error, "strdup() failed: %s", strerror(errno));
0155 #endif
0156         EXFAIL_OUT(ret);
0157     }
0158     
0159     
0160     EXHASH_ADD_KEYPTR( hh, (*h), tmp->str, strlen(tmp->str), tmp );
0161     
0162     
0163 out:
0164     if (EXSUCCEED==ret)
0165     {
0166         return tmp;
0167     }
0168     else
0169     {
0170         return NULL;
0171     }
0172 }
0173 
0174 
0175 
0176 
0177 
0178 
0179 
0180 expublic string_hash_t * ndrx_string_hash_get(string_hash_t *h, char *str)
0181 {
0182     string_hash_t * r = NULL;
0183     
0184     EXHASH_FIND_STR( h, str, r);
0185     
0186     return r;
0187 }
0188 
0189 
0190 
0191 
0192 
0193 
0194 expublic void ndrx_string_hash_free(string_hash_t *h)
0195 {
0196     string_hash_t * r, *rt;
0197     
0198     EXHASH_ITER(hh, h, r, rt)
0199     {
0200         EXHASH_DEL(h, r);
0201         NDRX_FREE(r->str);
0202         NDRX_FREE(r);
0203     }
0204 }
0205 
0206 
0207 
0208 
0209 expublic void ndrx_string_list_free(string_list_t* list)
0210 {
0211     string_list_t *elt, *tmp;
0212     
0213     if (NULL!=list)
0214     {
0215         LL_FOREACH_SAFE(list,elt,tmp) 
0216         {
0217             LL_DELETE(list,elt);
0218             if (NULL!=elt->qname)
0219             {
0220                 NDRX_FREE(elt->qname);
0221             }
0222             
0223             NDRX_FREE((char *)elt);
0224         }
0225     }
0226 }
0227 
0228 
0229 
0230 
0231 
0232 
0233 
0234 expublic int ndrx_string_list_add(string_list_t**list, char *string)
0235 {
0236     int ret = EXSUCCEED;
0237     string_list_t* tmp = NULL;
0238     
0239     if (NULL==(tmp = NDRX_CALLOC(1, sizeof(string_list_t))))
0240     {
0241         NDRX_LOG(log_error, "alloc of string_list_t (%d) failed", 
0242                 sizeof(string_list_t));
0243         EXFAIL_OUT(ret);
0244     }
0245     
0246     
0247     if (NULL==(tmp->qname = NDRX_STRDUP(string)))
0248     {
0249         NDRX_LOG(log_error, "Failed to strdup len (%d): %s", 
0250                strlen(string)+1, strerror(errno));
0251         NDRX_FREE(tmp);
0252         EXFAIL_OUT(ret);
0253     }
0254     
0255     
0256     LL_APPEND(*list, tmp);
0257     
0258  out:
0259     return ret;
0260 }
0261 
0262 
0263 
0264 
0265 
0266 
0267 
0268 
0269 
0270 expublic int ndrx_string_list_splitadd(string_list_t**list, char *string, char *sep)
0271 {
0272     int ret = EXSUCCEED;
0273     string_list_t* tmp = NULL;
0274     char *temps = NULL;
0275     char *tag;
0276     char *value_ptr;
0277     char *tag_first;
0278     char *ent;
0279     
0280     temps = NDRX_STRDUP(string);
0281     if (NULL==temps)
0282     {
0283         NDRX_LOG(log_error, "Failed to strdup: %s", strerror(errno));
0284         EXFAIL_OUT(ret);
0285     }
0286     
0287     tag_first = temps;
0288     
0289     NDRX_LOG(log_debug, "About token: [%s] by [%s]", tag_first, sep);
0290     
0291     while ((tag = strtok_r(tag_first, sep, &value_ptr)))
0292     {
0293         if (NULL!=tag_first)
0294         {
0295             tag_first = NULL; 
0296         }
0297         
0298         
0299         ent = ndrx_str_lstrip_ptr(tag, " \t");
0300         
0301         ndrx_str_rstrip(ent, " \t");
0302         
0303         
0304         if (NULL==(tmp = NDRX_CALLOC(1, sizeof(string_list_t))))
0305         {
0306             NDRX_LOG(log_error, "calloc of string_list_t (%d) failed", 
0307                     sizeof(string_list_t));
0308             EXFAIL_OUT(ret);
0309         }
0310         
0311         if (NULL==(tmp->qname = NDRX_STRDUP(ent)))
0312         {
0313             NDRX_LOG(log_error, "Failed to strdup len (%d): %s", 
0314                    strlen(ent)+1, strerror(errno));
0315             NDRX_FREE(tmp);
0316             EXFAIL_OUT(ret);
0317         }
0318         
0319         NDRX_LOG(log_debug, "Adding [%s]", tmp->qname);
0320         
0321         LL_APPEND(*list, tmp);
0322     }
0323     
0324  out:
0325     
0326     if (NULL!=temps)
0327     {
0328         NDRX_FREE(temps);
0329     }
0330  
0331     return ret;
0332 }
0333 
0334 
0335 
0336 
0337 
0338 
0339 
0340 
0341 expublic string_list_t * ndrx_sys_ps_getchilds(pid_t ppid)
0342 {
0343     
0344 
0345 
0346 
0347 
0348     char cmd[128];
0349     FILE *fp=NULL;
0350     string_list_t* ret = NULL;
0351     pid_t pid;
0352     char path[PATH_MAX];
0353     int is_error = EXFALSE;
0354     
0355 #ifdef EX_OS_FREEBSD
0356     
0357     NDRX_STRCPY_SAFE(cmd, "ps -wwaxo user,pid,ppid,%cpu,%mem,args");
0358 #elif EX_OS_SUNOS
0359     NDRX_STRCPY_SAFE(cmd, "ps -ef");
0360 #elif EX_OS_AIX
0361     NDRX_STRCPY_SAFE(cmd, "ps -ef");
0362 #else
0363     NDRX_STRCPY_SAFE(cmd, "ps -efww");
0364 #endif
0365     
0366     fp = popen(cmd, "r");
0367     
0368     if (fp == NULL)
0369     {
0370         NDRX_LOG(log_warn, "failed to run command [%s]: %s", cmd, strerror(errno));
0371         goto out;
0372     }
0373     
0374     while (fgets(path, sizeof(path)-1, fp) != NULL)
0375     {
0376         if (EXSUCCEED==ndrx_proc_ppid_get_from_ps(path, &pid) && ppid == pid)
0377         {
0378             if (EXSUCCEED!=ndrx_string_list_add(&ret, path))
0379             {
0380                 NDRX_LOG(log_error, "Failed to add [%s] to list of processes", path);
0381                 is_error = EXTRUE;
0382                 goto out;
0383             }
0384         }
0385     }
0386     
0387  out:
0388     
0389     if (fp!=NULL)
0390     {
0391         pclose(fp);
0392     }
0393  
0394     if (is_error)
0395     {
0396         ndrx_string_list_free(ret);
0397         ret = NULL;
0398     }
0399 
0400     return ret;
0401 }
0402     
0403 
0404 
0405 
0406 
0407 
0408 
0409 
0410 
0411 
0412 
0413 
0414 
0415 expublic string_list_t * ndrx_sys_ps_list(char *filter1, char *filter2, 
0416         char *filter3, char *filter4, char *regex1)
0417 {
0418     FILE *fp=NULL;
0419     char cmd[128];
0420     char path[PATH_MAX];
0421     int ok;
0422     int i;
0423     string_list_t* tmp;
0424     string_list_t* ret = NULL;
0425     regex_t r1;
0426     int r1_alloc = EXFALSE;
0427     int is_error = EXFALSE;
0428     
0429 #define MAX_FILTER      5
0430     char *filter[MAX_FILTER] = {filter1, filter2, filter3, filter4, regex1};
0431     
0432 #ifdef EX_OS_FREEBSD
0433     
0434     NDRX_STRCPY_SAFE(cmd, "ps -wwaxo user,pid,ppid,%cpu,%mem,args");
0435 #elif EX_OS_DARWIN
0436     
0437     NDRX_STRCPY_SAFE(cmd, "ps -je");
0438 #elif EX_OS_SUNOS
0439     NDRX_STRCPY_SAFE(cmd, "ps -ef");
0440 #elif EX_OS_AIX
0441     NDRX_STRCPY_SAFE(cmd, "ps -ef");
0442 #else
0443     NDRX_STRCPY_SAFE(cmd, "ps -efww");
0444 #endif
0445     
0446     if (EXEOS!=regex1[0])
0447     {
0448         if (EXSUCCEED!=ndrx_regcomp(&r1, regex1))
0449         {
0450             NDRX_LOG(log_error, "ndrx_sys_ps_list: Failed to compile regex1: [%s]", regex1);
0451             userlog("ndrx_sys_ps_list: Failed to compile regex1: [%s]", regex1);
0452             ret = NULL;
0453             goto out;
0454         }
0455         
0456         r1_alloc = EXTRUE;
0457     }
0458     
0459 #ifdef SYSCOMMON_ENABLE_DEBUG
0460     NDRX_LOG(log_debug, "Listing processes [%s] f1=[%s] f2=[%s] f3=[%s] f4=[%s] r1=[%s]", 
0461             cmd, filter1, filter2, filter3, filter4, regex1);
0462 #endif
0463     
0464     
0465     fp = popen(cmd, "r");
0466     if (fp == NULL)
0467     {
0468         userlog("failed to run command [%s]: %s", cmd, strerror(errno));
0469         goto out;
0470     }
0471     
0472     
0473     while (fgets(path, sizeof(path)-1, fp) != NULL)
0474     {
0475 
0476         
0477         
0478         ok = 0;
0479         
0480         for (i = 0; i<MAX_FILTER; i++)
0481         {
0482             
0483             if (EXEOS!=filter[i][0] && filter[i]==regex1 
0484                     && EXSUCCEED==ndrx_regexec(&r1, path))
0485             {
0486                 
0487                 ok++;
0488             }
0489             else if (EXEOS!=filter[i][0] && strstr(path, filter[i]))
0490             {
0491              
0492                 ok++;
0493             }
0494             else if (EXEOS==filter[i][0])
0495             {
0496                 
0497                 ok++;
0498             }
0499             else
0500             {
0501                 
0502             }
0503         }
0504         
0505         
0506         
0507         if (MAX_FILTER==ok)
0508         {
0509             
0510             ndrx_chomp(path);
0511             if (EXSUCCEED!=ndrx_string_list_add(&ret, path))
0512             {
0513                 is_error = EXTRUE;
0514                 goto out;
0515             }
0516         }
0517     }
0518 
0519 out:
0520     
0521     if (fp!=NULL)
0522     {
0523         pclose(fp);
0524     }
0525 
0526     if (r1_alloc)
0527     {
0528         ndrx_regfree(&r1);
0529     }
0530 
0531     if (is_error)
0532     {
0533         ndrx_string_list_free(ret);
0534         ret=NULL;
0535     }
0536 
0537     return ret;
0538     
0539 }
0540 
0541 
0542 
0543 
0544 
0545 
0546 
0547 
0548 expublic int ndrx_sys_ps_list2hash(string_list_t *plist, ndrx_intmap_t **hash)
0549 {
0550     string_list_t* elt = NULL;
0551     pid_t pid;
0552     pid_t ppid;
0553     int ret = EXSUCCEED;
0554     
0555     LL_FOREACH(plist,elt)
0556     {
0557         if (EXSUCCEED==ndrx_proc_pid_get_from_ps(elt->qname, &pid) &&
0558                 EXSUCCEED==ndrx_proc_ppid_get_from_ps(elt->qname, &ppid) &&
0559                 0!=pid &&
0560                 0!=ppid)
0561         {
0562             if (NULL==ndrx_intmap_add(hash, (int)pid, (int)ppid))
0563             {
0564                 EXFAIL_OUT(ret);
0565             }
0566         }
0567             
0568     }
0569     
0570 out:
0571     
0572     if (EXSUCCEED!=ret)
0573     {
0574         ndrx_intmap_remove (hash);
0575     }
0576 
0577     return ret;
0578 }
0579 
0580 
0581 
0582 
0583 
0584 
0585 
0586 
0587 
0588 expublic int ndrx_sys_ps_hash2parents(ndrx_intmap_t **pshash, int pid, ndrx_intmap_t **parents)
0589 {
0590     int ret = EXSUCCEED;    
0591     ndrx_intmap_t *cur = ndrx_intmap_find (pshash, pid);
0592     
0593     while (NULL!=cur)
0594     {
0595         if (NULL==ndrx_intmap_add (parents, cur->value, 0))
0596         {
0597             EXFAIL_OUT(ret);
0598         }
0599         
0600         
0601         cur = ndrx_intmap_find (pshash, cur->value);
0602     }
0603     
0604 out:
0605     return ret;
0606 }
0607 
0608 
0609 
0610 
0611 expublic char *ndrx_sys_get_cur_username(void)
0612 {
0613     uid_t uid = geteuid();
0614     struct passwd *pw = getpwuid(uid);
0615     if (pw)
0616     {
0617         return pw->pw_name;
0618     }
0619 
0620     return "";
0621 }
0622 
0623 
0624 
0625 
0626 
0627 
0628 
0629 expublic int ndrx_sys_get_hostname(char *out_hostname, long out_bufsz)
0630 {
0631     int ret = EXSUCCEED;
0632     
0633     if (EXSUCCEED!=gethostname(out_hostname, out_bufsz))
0634     {
0635         userlog("Failed to get hostname: %s", strerror(errno));
0636         EXFAIL_OUT(ret);
0637     }
0638     
0639 out:
0640     return ret;
0641 }
0642 
0643 
0644 
0645 
0646 expublic string_list_t* ndrx_sys_folder_list(char *path, int *return_status)
0647 {
0648     string_list_t* ret = NULL;
0649     struct dirent **namelist;
0650     int n, i;
0651     string_list_t* tmp;
0652     int len;
0653     
0654     *return_status = EXSUCCEED;
0655     
0656     n = scandir(path, &namelist, 0, alphasort);
0657     if (n < 0)
0658     {
0659         
0660 #ifdef SYSCOMMON_ENABLE_DEBUG
0661         NDRX_LOG(log_error, "Failed to open queue directory [%s]: %s", 
0662                 path, strerror(errno));
0663 #endif
0664         goto exit_fail;
0665     }
0666     else 
0667     {
0668         for (i=0; i<n; i++)
0669         {
0670             
0671             if (0==strcmp(namelist[i]->d_name, ".") || 
0672                         0==strcmp(namelist[i]->d_name, ".."))
0673             {
0674                 NDRX_FREE(namelist[i]);
0675                 continue;
0676             }
0677             
0678             len = 1  + strlen(namelist[i]->d_name) + 1 ;
0679             
0680             if (NULL==(tmp = NDRX_CALLOC(1, sizeof(string_list_t))))
0681             {
0682                 
0683 #ifdef SYSCOMMON_ENABLE_DEBUG
0684                 NDRX_LOG(log_error, "alloc of mq_list_t (%d) failed: %s", 
0685                         sizeof(string_list_t), strerror(errno));
0686 #endif
0687                 goto exit_fail;
0688             }
0689             
0690             if (NULL==(tmp->qname = NDRX_MALLOC(len)))
0691             {
0692                 
0693 #ifdef SYSCOMMON_ENABLE_DEBUG
0694                 NDRX_LOG(log_error,"alloc of %d bytes failed: %s", 
0695                         len, strerror(errno));
0696 #endif
0697                 NDRX_FREE(tmp);
0698                 goto exit_fail;
0699             }
0700             
0701             
0702             strcpy(tmp->qname, "/");
0703             strcat(tmp->qname, namelist[i]->d_name);
0704             
0705             
0706             LL_APPEND(ret, tmp);
0707             
0708             NDRX_FREE(namelist[i]);
0709         }
0710         NDRX_FREE(namelist);
0711     }
0712     
0713     return ret;
0714     
0715 exit_fail:
0716 
0717     *return_status = EXFAIL;
0718 
0719     if (NULL!=ret)
0720     {
0721         ndrx_string_list_free(ret);
0722         ret = NULL;
0723     }
0724 
0725     return ret;   
0726 }
0727 
0728 
0729 
0730 
0731 
0732 expublic void ndrx_proc_kill_list(string_list_t *list)
0733 {
0734     string_list_t* elt = NULL;
0735     int signals[] = {SIGTERM, SIGKILL};
0736     int i;
0737     int max_signals = 2;
0738     int was_any = EXFALSE;
0739     pid_t pid;
0740     char *fn = "ndrx_proc_kill_list";
0741     NDRX_LOG(log_info, "%s enter-> %p", fn, list);
0742     
0743     for (i=0; i<max_signals; i++)
0744     {
0745         LL_FOREACH(list,elt)
0746         {
0747             if (EXSUCCEED==ndrx_proc_pid_get_from_ps(elt->qname, &pid))
0748             {
0749                  NDRX_LOG(log_error, "! killing  sig=%d "
0750                          "pid=[%d] (%s)", signals[i], pid, elt->qname);
0751 
0752                  if (EXSUCCEED!=kill(pid, signals[i]))
0753                  {
0754                      NDRX_LOG(log_error, "failed to kill with signal %d pid %d: %s",
0755                              signals[i], pid, strerror(errno));
0756                  }
0757                  else
0758                  {
0759                     was_any = EXTRUE;
0760                  }
0761             }    
0762         } 
0763         
0764         if (was_any && i<max_signals-1)
0765         {
0766             
0767             sleep(EX_KILL_SLEEP_SECS);
0768         }
0769         
0770     } 
0771     
0772 }
0773 
0774 
0775 
0776 
0777 
0778 
0779 
0780 
0781 
0782 expublic int ndrx_proc_children_get_recursive(string_list_t**list, pid_t pid)
0783 {
0784     int ret = EXSUCCEED;
0785     string_list_t* elt = NULL;
0786     string_list_t* children = NULL;
0787     
0788     char *fn = "ndrx_get_childproc_recursive";
0789     NDRX_LOG(log_info, "%s enter-> list=%p, pid=%d", fn, list, pid);
0790     
0791     children = ndrx_sys_ps_getchilds(pid);
0792     
0793     LL_FOREACH(children,elt)
0794     {
0795         if (EXSUCCEED==ndrx_proc_pid_get_from_ps(elt->qname, &pid))
0796         {
0797             
0798             if (EXSUCCEED!=ndrx_proc_children_get_recursive(list, pid))
0799             {
0800                 EXFAIL_OUT(ret);
0801             }
0802             
0803             if (EXSUCCEED!=ndrx_string_list_add(list, elt->qname))
0804             {
0805                 EXFAIL_OUT(ret);
0806             }
0807     
0808         }
0809     } 
0810     
0811 out:
0812     ndrx_string_list_free(children);
0813     return ret;
0814 }
0815 
0816 
0817 
0818 
0819 
0820 
0821 
0822 expublic int ndrx_proc_pid_get_from_ps(char *psout, pid_t *pid)
0823 {
0824     char tmp[PATH_MAX+1];
0825     char *token;
0826     int ret = EXSUCCEED;
0827     
0828     NDRX_STRCPY_SAFE(tmp, psout);
0829 
0830     
0831     if (NULL==(token = strtok(tmp, "\t ")))
0832     {
0833         NDRX_LOG(log_error, "missing username in ps -ef output");
0834         EXFAIL_OUT(ret);
0835     }
0836 
0837     
0838     token = strtok(NULL, "\t ");
0839     if (NULL==token)
0840     {
0841         NDRX_LOG(log_error, "missing pid in ps -ef output");
0842         EXFAIL_OUT(ret);
0843     }   
0844     else
0845     {
0846         *pid = atoi(token);
0847 #ifdef SYSCOMMON_ENABLE_DEBUG
0848         NDRX_LOG(log_debug, "ndrx_get_pid_from_ps: Got %d as pid of [%s]", *pid, psout);
0849 #endif
0850     }
0851     
0852 out:
0853     return ret;
0854 }
0855 
0856 
0857 
0858 
0859 
0860 
0861 
0862 
0863 expublic int ndrx_proc_get_line(int line_no, char *cmd, char *buf, int bufsz)
0864 {
0865     int ret = EXSUCCEED;
0866     FILE *fp=NULL;
0867     int line = 0;
0868     NDRX_LOG(log_debug, "%s: About to run: [%s]", __func__, cmd);
0869     
0870     fp = popen(cmd, "r");
0871     if (fp == NULL)
0872     {
0873 #ifdef SYSCOMMON_ENABLE_DEBUG
0874         NDRX_LOG(log_warn, "failed to run command [%s]: %s", cmd, strerror(errno));
0875 #endif
0876         EXFAIL_OUT(ret);
0877     }
0878     
0879     while (fgets(buf, bufsz, fp) != NULL)
0880     {
0881         line ++;
0882         
0883         if (line==line_no)
0884         {
0885             break;
0886         }
0887     }
0888 
0889 out:
0890 
0891     
0892     if (fp!=NULL)
0893     {
0894         pclose(fp);
0895     }
0896 
0897     if (line!=line_no)
0898     {
0899         NDRX_LOG(log_error, "Extract lines: %d, but requested: %d", 
0900                 line, line_no);
0901         ret=EXFAIL;
0902     }
0903 
0904     if (EXSUCCEED==ret)
0905     {
0906         ndrx_chomp(buf);
0907     }
0908 
0909     return ret;   
0910 }
0911 
0912 
0913 
0914 
0915 
0916 
0917 
0918 expublic int ndrx_proc_ppid_get_from_ps(char *psout, pid_t *ppid)
0919 {
0920     char tmp[PATH_MAX+1];
0921     char *token;
0922     int ret = EXSUCCEED;
0923     
0924     NDRX_STRCPY_SAFE(tmp, psout);
0925 
0926     
0927     if (NULL==(token = strtok(tmp, "\t ")))
0928     {
0929         NDRX_LOG(log_error, "missing username in ps -ef output (1)");
0930         EXFAIL_OUT(ret);
0931     }
0932 
0933     
0934     token = strtok(NULL, "\t ");
0935     if (NULL==token)
0936     {
0937         NDRX_LOG(log_error, "missing pid in ps -ef output (2)");
0938         EXFAIL_OUT(ret);
0939     }
0940     
0941     
0942     token = strtok(NULL, "\t ");
0943     if (NULL==token)
0944     {
0945         NDRX_LOG(log_error, "missing pid in ps -ef output (3)");
0946         EXFAIL_OUT(ret);
0947     }
0948     else
0949     {
0950         *ppid = atoi(token);
0951 #ifdef SYSCOMMON_ENABLE_DEBUG
0952         NDRX_LOG(log_debug, "Got %d as parent pid of [%s]", *ppid, psout);
0953 #endif
0954     }
0955     
0956 out:
0957     return ret;
0958 }
0959 
0960 
0961 
0962 
0963 
0964 
0965 
0966 
0967 expublic int ndrx_proc_get_infos(pid_t pid, ndrx_proc_info_t *p_infos)
0968 {
0969     int ret = EXSUCCEED;
0970     char cmd[128];
0971     char line[PATH_MAX+1];
0972     long  meminfo[16];
0973     int toks;
0974 
0975 
0976 
0977 
0978 
0979 
0980 
0981 
0982 
0983 
0984 
0985 
0986 
0987 
0988 
0989 
0990 
0991     
0992 #ifdef EX_OS_AIX
0993     snprintf(cmd, sizeof(cmd), "ps v %d", pid);
0994     
0995     if (EXSUCCEED!=ndrx_proc_get_line(2, cmd, line, sizeof(line)))
0996     {
0997         NDRX_LOG(log_error, "Failed to get rss infos from  [%s]", cmd);
0998         EXFAIL_OUT(ret);
0999     }
1000     
1001     NDRX_LOG(log_debug, "Parsing output: [%s]", line);
1002     
1003     toks = ndrx_tokens_extract(line, "%ld", (void *)meminfo, 
1004             sizeof(long), N_DIM(meminfo), 0, 15);
1005     
1006     if (toks<7)
1007     {
1008         NDRX_LOG(log_error, "Invalid tokens, expected at least 7, got %d", toks);
1009        EXFAIL_OUT(ret);
1010     }
1011     
1012     p_infos->rss = meminfo[6];
1013     
1014     snprintf(cmd, sizeof(cmd), "ps -o vsz -p %d", pid);
1015     
1016     if (EXSUCCEED!=ndrx_proc_get_line(2, cmd, line, sizeof(line)))
1017     {
1018         NDRX_LOG(log_error, "Failed to get rss infos from  [%s]", cmd);
1019         EXFAIL_OUT(ret);
1020     }
1021     
1022     NDRX_LOG(log_debug, "Parsing output: [%s]", line);
1023     
1024     toks = ndrx_tokens_extract(line, "%ld", (void *)meminfo, 
1025             sizeof(long), N_DIM(meminfo), 0, 15);
1026     
1027     if (toks!=1)
1028     {
1029        NDRX_LOG(log_error, "Invalid tokens, expected at least 1, got %d", toks);
1030        EXFAIL_OUT(ret);
1031     }
1032     
1033     p_infos->vsz = meminfo[0];  
1034     
1035 #else
1036     
1037     snprintf(cmd, sizeof(cmd), "ps -o rss,vsz -p%d", pid);
1038     
1039     if (EXSUCCEED!=ndrx_proc_get_line(2, cmd, line, sizeof(line)))
1040     {
1041         NDRX_LOG(log_error, "Failed to get rss/vsz infos from  [%s]", cmd);
1042         EXFAIL_OUT(ret);
1043     }
1044     
1045     NDRX_LOG(log_debug, "Parsing output: [%s]", line);
1046     
1047     toks = ndrx_tokens_extract(line, "%ld", (void *)meminfo, 
1048             sizeof(long), N_DIM(meminfo), 0, 15);
1049     
1050     if (2!=toks)
1051     {
1052        NDRX_LOG(log_error, "Invalid tokens, expected 2, got %d", toks);
1053        EXFAIL_OUT(ret);
1054     }
1055     
1056     p_infos->rss = meminfo[0];
1057     p_infos->vsz = meminfo[1];
1058     
1059 #endif
1060     
1061  
1062     NDRX_LOG(log_info, "extracted rss=%ld vsz=%ld", p_infos->rss, p_infos->vsz);
1063     
1064 out:
1065     
1066     NDRX_LOG(log_debug, "%s: returns %d", __func__, ret);
1067 
1068     return ret;
1069 }
1070 
1071 
1072 
1073 
1074 
1075 
1076 
1077 
1078 
1079 
1080 expublic int ndrx_sys_cmdout_test(char *fmt, pid_t pid, regex_t *p_re)
1081 {
1082     char cmd[PATH_MAX];
1083     FILE *fp=NULL;
1084     char *buf = NULL;
1085     size_t n = PATH_MAX;
1086     int ret = EXSUCCEED;
1087     
1088     
1089     
1090     NDRX_MALLOC_OUT(buf, n, char);
1091     
1092     snprintf(cmd, sizeof(cmd), fmt, pid);
1093     
1094     fp = popen(cmd, "r");
1095     
1096     if (fp == NULL)
1097     {
1098         NDRX_LOG(log_warn, "failed to run command [%s]: %s", cmd, strerror(errno));
1099         goto out;
1100     }
1101     
1102     while (EXFAIL!=ndrx_getline(&buf, &n, fp))
1103     {
1104         
1105         if (EXSUCCEED==ndrx_regexec(p_re, buf))
1106         {
1107             NDRX_LOG(log_debug, "Matched env [%s] for pid %d", buf, (int)pid);
1108             ret=EXTRUE;
1109             goto out;
1110         }
1111     }
1112     
1113  out:
1114                 
1115     
1116     if (fp!=NULL)
1117     {
1118         pclose(fp);
1119     }
1120  
1121     if (NULL!=buf)
1122     {
1123         NDRX_FREE(buf);
1124     }
1125  
1126     return ret;
1127 }
1128 
1129 
1130 
1131 
1132 expublic void ndrx_sys_banner(void)
1133 {
1134     NDRX_BANNER("");
1135 }
1136 
1137 
1138 
1139 
1140 expublic void ndrx_atfork_prepare(void)
1141 {
1142     
1143 #ifndef USE_STOCK_FORKING
1144     int i;
1145     
1146     for (i=MAX_ATFORKS-1; i>=0; i--)
1147     {
1148         if (NULL!=M_prepare[i])
1149         {
1150             M_prepare[i]();
1151         }
1152     }
1153 #endif
1154 }
1155 
1156 
1157 
1158 
1159 expublic void ndrx_atfork_parent(void)
1160 {
1161 #ifndef USE_STOCK_FORKING
1162     int i;
1163     for (i=0; i<MAX_ATFORKS; i++)
1164     {
1165         if (NULL!=M_parent[i])
1166         {
1167             M_parent[i]();
1168         }
1169     }
1170 #endif
1171 }
1172 
1173 
1174 
1175 
1176 expublic void ndrx_atfork_child(void)
1177 {
1178 #ifndef USE_STOCK_FORKING
1179     int i;
1180     
1181     
1182     ndrx_dbg_pid_update();
1183     
1184     for (i=0; i<MAX_ATFORKS; i++)
1185     {
1186         if (NULL!=M_child[i])
1187         {
1188             M_child[i]();
1189         }
1190     }
1191 #endif
1192 }
1193 
1194 
1195 
1196 
1197 
1198 
1199 
1200 
1201 
1202 
1203 
1204 
1205 expublic pid_t ndrx_fork(void)
1206 {
1207     pid_t ret;
1208     int err;
1209     
1210 #ifdef USE_STOCK_FORKING
1211     
1212     ret = fork();
1213     err = errno;
1214     
1215     
1216     if (0==ret)
1217     {
1218         ndrx_dbg_pid_update();
1219     }
1220     
1221     return ret;
1222     
1223 #else
1224     
1225     ndrx_atfork_prepare();
1226     
1227     ret = fork();
1228     err = errno;
1229     
1230     if (0==ret)
1231     {
1232         ndrx_atfork_child();
1233     }
1234     else
1235     {
1236         ndrx_atfork_parent();
1237     }
1238     
1239     errno = err;
1240     
1241     return ret;
1242 #endif
1243 }
1244 
1245 
1246 
1247 
1248 
1249 
1250 
1251 
1252 
1253 expublic int ndrx_atfork(void (*prepare)(void), void (*parent)(void),
1254        void (*child)(void))
1255 {
1256 #ifdef USE_STOCK_FORKING
1257     return pthread_atfork(prepare, parent, child);
1258 #else
1259     int i=0;
1260     int ret = EXSUCCEED;
1261 
1262     for (i=0;i<MAX_ATFORKS;i++)
1263     {
1264         
1265         
1266         
1267         if (prepare==M_prepare[i] && 
1268                 parent==M_parent[i] &&
1269                 child==M_child[i]
1270             )
1271         {
1272             
1273             goto out;
1274         }
1275         
1276         if (NULL==M_prepare[i] && 
1277                 NULL==M_parent[i] &&
1278                 NULL==M_child[i]
1279             )
1280         {
1281             break;
1282         }
1283     }
1284     
1285     if (i==MAX_ATFORKS)
1286     {
1287         errno=ENOMEM;
1288         EXFAIL_OUT(ret);
1289     }
1290     
1291     M_prepare[i] = prepare;
1292     M_parent[i] = parent;
1293     M_child[i] = child;
1294     
1295 out:
1296     return ret;
1297 #endif
1298 }
1299 
1300 
1301 
1302 
1303 
1304 
1305 
1306 expublic int ndrx_sys_sysv_user_res(ndrx_growlist_t *list, int res_type)
1307 {
1308     char cmd[128];
1309     FILE *fp=NULL;
1310     char path[PATH_MAX];
1311     char linematchstr[PATH_MAX];
1312     int ret = EXSUCCEED;
1313     regex_t linematch;
1314     int linematch_comp = EXFALSE;
1315     int sig_set = EXFALSE;
1316     struct sigaction act;
1317     
1318     
1319     ndrx_growlist_init(list, 256, sizeof(mdrx_sysv_res_t));
1320     
1321     if (NDRX_SV_RESTYPE_QUE == res_type)
1322     {
1323         NDRX_STRCPY_SAFE(cmd, "ipcs -q");
1324         
1325 
1326 
1327 
1328 
1329 
1330 
1331 
1332 
1333 
1334 
1335 
1336 
1337 
1338 
1339 
1340 
1341 
1342 
1343 
1344 
1345 
1346 
1347 
1348 
1349 
1350 
1351 
1352 
1353 
1354 
1355 
1356 
1357 
1358 
1359 
1360 
1361 
1362 
1363 
1364 
1365 
1366 
1367 
1368 
1369 
1370 
1371 
1372 
1373     }
1374     else if (NDRX_SV_RESTYPE_SEM == res_type)
1375     {
1376         NDRX_STRCPY_SAFE(cmd, "ipcs -s");
1377         
1378 
1379 
1380 
1381 
1382 
1383 
1384 
1385 
1386 
1387 
1388     }
1389     else if (NDRX_SV_RESTYPE_SHM == res_type)
1390     {
1391         NDRX_STRCPY_SAFE(cmd, "ipcs -m");
1392     }
1393 #ifdef EX_OS_LINUX
1394     snprintf(linematchstr, sizeof(linematchstr), "^0x[0-9a-fA-F]+\\s*[0-9]+\\s*%s\\s",
1395             ndrx_sys_get_cur_username());
1396 #else
1397     snprintf(linematchstr, sizeof(linematchstr), "^.[ \\t\\r\\n\\v\\f]+[0-9]+[ \\t\\r\\n\\v\\f]+[x0-9a-fA-F]*[ \\t\\r\\n\\v\\f]+.{11}[ \\t\\r\\n\\v\\f]+%s[ \\t\\r\\n\\v\\f]",
1398             ndrx_sys_get_cur_username());
1399 #endif
1400     
1401     if (EXSUCCEED!=ndrx_regcomp(&linematch, linematchstr))
1402     {
1403         userlog("Failed to compile regexp: %s", linematch);
1404         NDRX_LOG(log_error, "Failed to compile regexp: %s", linematch);
1405         EXFAIL_OUT(ret);
1406     }
1407     else
1408     {
1409         linematch_comp = EXTRUE;
1410     }
1411     
1412     NDRX_LOG(log_debug, "Listing resources by: [%s]", cmd);
1413     
1414     
1415     sigaction(SIGCHLD, NULL, &act);
1416     signal(SIGCHLD, SIG_DFL);
1417     sig_set=EXTRUE;
1418     
1419     fp = popen(cmd, "r");
1420     
1421     if (fp == NULL)
1422     {
1423         NDRX_LOG(log_warn, "failed to run command [%s]: %s", cmd, strerror(errno));
1424         goto out;
1425     }
1426     
1427     while (fgets(path, sizeof(path)-1, fp) != NULL)
1428     {        
1429         if (EXSUCCEED==ndrx_regexec(&linematch, path))
1430         {
1431             int id;
1432             int key;
1433             int len = strlen(path);
1434             mdrx_sysv_res_t res;
1435             
1436             if (len > 0 && '\n' == path[len-1])
1437             {
1438                 path[len-1]=EXEOS;
1439             }
1440             
1441             NDRX_LOG(log_debug, "Line matched: [%s]", path);
1442             
1443             
1444             if (1!=ndrx_tokens_extract(path, "%d", &id, sizeof(id), 1, 1, 1))
1445             {
1446                 NDRX_LOG(log_error, "Failed to extract resource id from [%s]!",
1447                         path);
1448                 userlog("Failed to extract resource id from [%s]!",
1449                         path);
1450                 EXFAIL_OUT(ret);
1451             }
1452          
1453             NDRX_LOG(log_debug, "Extract id %u", id);
1454             
1455 #if EX_OS_LINUX
1456       
1457             
1458             if (1!=ndrx_tokens_extract(path, "%x", &key, sizeof(key), 1, 0, 0))
1459             {
1460                 NDRX_LOG(log_error, "Failed to extract resource key from [%s]!",
1461                         path);
1462                 userlog("Failed to extract resource key from [%s]!",
1463                         path);
1464                 EXFAIL_OUT(ret);
1465             }
1466          
1467             NDRX_LOG(log_debug, "Extract key %u", key);
1468 #else
1469             
1470             
1471             if (1!=ndrx_tokens_extract(path, "%x", &key, sizeof(key), 1, 2, 2))
1472             {
1473                 NDRX_LOG(log_error, "Failed to extract resource key from [%s]!",
1474                         path);
1475                 userlog("Failed to extract resource key from [%s]!",
1476                         path);
1477                 EXFAIL_OUT(ret);
1478             }
1479          
1480             NDRX_LOG(log_debug, "Extract key %u", key);
1481             
1482 #endif
1483             
1484             
1485             res.id=id;
1486             res.key = key;
1487             res.restyp=res_type;
1488             
1489             if (EXSUCCEED!=ndrx_growlist_append(list, (void *)&res))
1490             {
1491                 NDRX_LOG(log_error, "Failed to add %u/%u to growlist!", id, key);
1492                 userlog("Failed to add %u/%u to growlist!", id, key);
1493                 EXFAIL_OUT(ret);
1494             }
1495         }
1496     }
1497     
1498  out:
1499     
1500     if (fp!=NULL)
1501     {
1502         pclose(fp);
1503     }
1504  
1505     if (sig_set)
1506     {
1507         sigaction(SIGCHLD, &act, NULL);
1508     }
1509  
1510     if (EXSUCCEED!=ret)
1511     {
1512         ndrx_growlist_free(list);
1513     }
1514  
1515     if (linematch_comp)
1516     {
1517         ndrx_regfree(&linematch);
1518     }
1519 
1520     return ret;
1521 }
1522 
1523