#include #include #include #include "ostool.h" #include "commun.h" #include "common.m" struct HOMEPATH{ char path[MAXSIZ_PATH]; int len; }; /* Determine si un path est un sous-repertoire d'un autre. Retourne la longueur du path modifi‚ ou -1. */ static int near path_issub ( const char *path, HOMEPATH &home, const char *prefix, char *dst) // Recoit le resultat si ok { int ret = -1; if (home.len > 0 && strncmp(home.path,path,home.len)==0 && (path[home.len] == '\0' || path_issep(path[home.len]))){ char *pt = stpcpy (dst,prefix); pt = stpcpy (pt,path+home.len); ret = (int)(pt - dst); } return ret; } /* Convertit un path en path relatif a HOME (avec ~). Le path r‚sultant n'est pas utilisable directement. Il ne sert qu'… l'affichage. Retourne -1 si ce n'est pas possible (path trop distant de HOME) Dans ce cas, dst contiendra src sans changement. Retourne la longueur du path plac‚ dans dst si ok. Le traitement sera fait si src est un sous-r‚pertoire de HOME ou si src est un sous-r‚pertoire du r‚pertoire ancˆtre de HOME. */ export int path_cnv2home ( const char *src, char *dst) { static char is_init = 0; static HOMEPATH home,cnv_home,papa,cnv_papa; if (!is_init){ char *pt = getenv("HOME"); home.len = papa.len = cnv_home.len = cnv_papa.len = 0; if (pt != NULL){ strcpy (home.path,pt); path_cnv2reel (pt,cnv_home.path); path_splitlex (home.path,papa.path,NULL); path_splitlex (cnv_home.path,cnv_papa.path,NULL); home.len = strlen(home.path); papa.len = strlen(papa.path); cnv_home.len = strlen(cnv_home.path); cnv_papa.len = strlen(cnv_papa.path); } is_init = 1; } strcpy (dst,src); int ret = path_issub (src,home,"~",dst); if (ret == -1) ret = path_issub(src,cnv_home,"~",dst); if (ret == -1) ret = path_issub(src,papa,"~/..",dst); if (ret == -1) ret = path_issub(src,cnv_papa,"~/..",dst); return ret; } /* Limite la pr‚sentation visuelle d'un path. Le d‚but est tronqu‚ et on insŠre "..." pour confirmer que le d‚but est manquant. Retourne path si path est moins long que maxpath, ou tmppath qui contient le path l‚gŠrement modifi‚. Cette fonction ne peut servir que pour pr‚sentation seulement. Transforme aussi le path relatif a HOME si cela reduit sa longueur. */ export const char *path_limit ( const char *path, char *tmppath, int maxpath) { char homepath[MAXSIZ_PATH]; int lenhome = path_cnv2home (path,homepath); int lenpath = strlen(path); if (lenhome > 0 && lenhome < lenpath){ lenpath = lenhome; path = homepath; } if (lenpath > maxpath){ strcpy (tmppath,"..."); strcpy (tmppath+3,path+(lenpath-maxpath)+3); path = tmppath; }else if (path == homepath){ strcpy (tmppath,path); path = tmppath; } return path; } /* Convertit un path d‚butant par un tilde en ins‚rant la variable HOME. Retourne != 0 si le path d‚butait effectivement par un ~/ dst contiendra la conversion ou simplement une copie de src. dst peut ˆtre la mˆme que src. */ export int path_cnvtilde (const char *src, char *dst) { int ret = 0; if (src[0] == '~' && path_issep(src[1])){ /* #Sp‚cification: path / tilde La s‚quence ~/ ou ~\ (d‚pendant de l'OS) est remplac‚ par la variable d'environnement HOME si elle existe. */ char *home = getenv("HOME"); if (home == NULL){ fprintf (stderr,MSG_U(E_NOHOME , "Variable d'environnement HOME non d‚finie\n" "Ne peut pas r‚soudre %s\n") ,src); }else{ char tmp[MAXSIZ_PATH]; strcpy (tmp,src+2); path_make (home,tmp,dst); ret = 1; } } if (ret == 0 && src != dst) strcpy (dst,src); return ret; } #ifdef TEST static void testhome (const char *path) { char rpath[MAXSIZ_PATH]; path_cnv2reel(path,rpath); char res[MAXSIZ_PATH]; int ret = path_cnv2home (path,res); printf ("\t:%s: -> :%s:\n",path,res); char rres[MAXSIZ_PATH]; int rret = path_cnv2home (rpath,rres); printf ("\t:%s: -> :%s:\n",rpath,rres); if (ret != rret){ printf ("\t\tret != rret %d <> %d\n",ret,rret); }else if (ret != -1 && strcmp(res,rres)!=0){ printf ("\t\tResultat different\n"); } } static void testlimit (const char *path) { char rpath[MAXSIZ_PATH]; path_cnv2reel(path,rpath); char res[MAXSIZ_PATH]; const char *ret = path_limit (path,res,40); printf ("\t:%s: -> :%s:\n",path,ret); char rres[MAXSIZ_PATH]; const char *rret = path_limit (rpath,rres,40); printf ("\t:%s: -> :%s:\n",rpath,rret); } static void test (const char *path) { printf ("----- %s ------\n",path); testhome (path); testlimit (path); } int main (int argc, char *argv[]) { if (argc > 1 ){ for (int i=1; i