• Main Page
  • Related Pages
  • Data Structures
  • Files
  • File List
  • Globals

list.c

Go to the documentation of this file.
00001 
00016 #include <stdlib.h>
00017 #include <unistd.h>
00018 #include <signal.h>
00019 #include <string.h>
00020 #include <sys/types.h>
00021 #include <dirent.h>
00022 
00023 #include <grass/gis.h>
00024 #include <grass/glocale.h>
00025 
00026 static int broken_pipe;
00027 static int hit_return = 0;
00028 static int list_element(FILE *, const char *, const char *, const char *,
00029                         int (*)(const char *, const char *, const char *));
00030 static RETSIGTYPE sigpipe_catch(int);
00031 
00032 int G_set_list_hit_return(int flag)
00033 {
00034     hit_return = flag;
00035     return 0;
00036 }
00037 
00060 int G_list_element(const char *element,
00061                    const char *desc,
00062                    const char *mapset,
00063                    int (*lister) (const char *, const char *, const char *))
00064 {
00065     int n;
00066     FILE *more;
00067     int count;
00068 
00069 #ifdef SIGPIPE
00070     RETSIGTYPE (*sigpipe)(int);
00071 #endif
00072 
00073     /* must catch broken pipe in case "more" quits */
00074     broken_pipe = 0;
00075 #ifdef SIGPIPE
00076     sigpipe = signal(SIGPIPE, sigpipe_catch);
00077 #endif
00078 
00079     count = 0;
00080     if (desc == 0 || *desc == 0)
00081         desc = element;
00082 
00083 #ifndef __MINGW32__
00084     /*
00085      * popen() the more command to page the output
00086      */
00087     if (isatty(1)) {
00088 #ifdef __MINGW32__
00089         more = popen("%GRASS_PAGER%", "w");
00090 #else
00091         more = popen("$GRASS_PAGER", "w");
00092 #endif
00093         if (!more)
00094             more = stdout;
00095     }
00096     else
00097 #endif
00098         more = stdout;
00099     fprintf(more, "----------------------------------------------\n");
00100 
00101     /*
00102      * if no specific mapset is requested, list the mapsets
00103      * from the mapset search list
00104      * otherwise just list the specified mapset
00105      */
00106     if (mapset == 0 || *mapset == 0)
00107         for (n = 0; !broken_pipe && (mapset = G__mapset_name(n)); n++)
00108             count += list_element(more, element, desc, mapset, lister);
00109     else
00110         count += list_element(more, element, desc, mapset, lister);
00111 
00112     if (!broken_pipe) {
00113         if (count == 0) {
00114             if (mapset == 0 || *mapset == 0)
00115                 fprintf(more, _("no %s files available in current mapset\n"),
00116                         desc);
00117             else
00118                 fprintf(more, _("no %s files available in mapset <%s>\n"),
00119                         desc, mapset);
00120         }
00121 
00122         fprintf(more, "----------------------------------------------\n");
00123     }
00124     /*
00125      * close the more
00126      */
00127     if (more != stdout)
00128         G_pclose(more);
00129 #ifdef SIGPIPE
00130     signal(SIGPIPE, sigpipe);
00131 #endif
00132     if (hit_return && isatty(1)) {
00133         fprintf(stderr, _("hit RETURN to continue -->"));
00134         while (getchar() != '\n') ;
00135     }
00136 
00137     return 0;
00138 }
00139 
00140 static RETSIGTYPE sigpipe_catch(int n)
00141 {
00142     broken_pipe = 1;
00143     signal(n, sigpipe_catch);
00144 }
00145 
00146 static int list_element(FILE * out,
00147                         const char *element, const char *desc,
00148                         const char *mapset, int (*lister) (const char *,
00149                                                            const char *,
00150                                                            const char *))
00151 {
00152     char path[GPATH_MAX];
00153     int count = 0;
00154     char **list;
00155     int i;
00156 
00157     /*
00158      * convert . to current mapset
00159      */
00160     if (strcmp(mapset, ".") == 0)
00161         mapset = G_mapset();
00162 
00163 
00164     /*
00165      * get the full name of the GIS directory within the mapset
00166      * and list its contents (if it exists)
00167      *
00168      * if lister() routine is given, the ls command must give 1 name
00169      */
00170     G__file_name(path, element, "", mapset);
00171     if (access(path, 0) != 0) {
00172         fprintf(out, "\n");
00173         return count;
00174     }
00175 
00176     /*
00177      * if a title so that we can call lister() with the names
00178      * otherwise the ls must be forced into columnar form.
00179      */
00180 
00181     list = G__ls(path, &count);
00182 
00183     if (count > 0) {
00184         fprintf(out, _("%s files available in mapset <%s>:\n"), desc, mapset);
00185         if (lister) {
00186             char title[400];
00187             char name[GNAME_MAX];
00188 
00189             *name = *title = 0;
00190             lister(name, mapset, title);
00191             if (*title)
00192                 fprintf(out, "\n%-18s %-.60s\n", name, title);
00193         }
00194     }
00195 
00196     if (lister) {
00197         for (i = 0; i < count; i++) {
00198             char title[400];
00199 
00200             lister(list[i], mapset, title);
00201             fprintf(out, "%-18s %-.60s\n", list[i], title);
00202         }
00203     }
00204     else
00205         G_ls_format(list, count, 0, out);
00206 
00207     fprintf(out, "\n");
00208 
00209     for (i = 0; i < count; i++)
00210         G_free((char *)list[i]);
00211     if (list)
00212         G_free(list);
00213 
00214     return count;
00215 }
00216 
00227 char **G_list(int element, const char *gisbase, const char *location,
00228               const char *mapset)
00229 {
00230     char *el;
00231     char *buf;
00232     DIR *dirp;
00233     struct dirent *dp;
00234     int count;
00235     char **list;
00236 
00237     switch (element) {
00238     case G_ELEMENT_RASTER:
00239         el = "cell";
00240         break;
00241 
00242     case G_ELEMENT_GROUP:
00243         el = "group";
00244         break;
00245 
00246     case G_ELEMENT_VECTOR:
00247         el = "vector";
00248         break;
00249 
00250     case G_ELEMENT_REGION:
00251         el = "windows";
00252         break;
00253 
00254     default:
00255         G_fatal_error(_("G_list: Unknown element type"));
00256     }
00257 
00258     buf = (char *)G_malloc(strlen(gisbase) + strlen(location)
00259                            + strlen(mapset) + strlen(el) + 4);
00260 
00261     sprintf(buf, "%s/%s/%s/%s", gisbase, location, mapset, el);
00262 
00263     dirp = opendir(buf);
00264     G_free(buf);
00265 
00266     if (dirp == NULL) {         /* this can happen if element does not exist */
00267         list = (char **)G_calloc(1, sizeof(char *));
00268         return list;
00269     }
00270 
00271     count = 0;
00272     while ((dp = readdir(dirp)) != NULL) {
00273         if (dp->d_name[0] == '.')
00274             continue;
00275         count++;
00276     }
00277     rewinddir(dirp);
00278 
00279     list = (char **)G_calloc(count + 1, sizeof(char *));
00280 
00281     count = 0;
00282     while ((dp = readdir(dirp)) != NULL) {
00283         if (dp->d_name[0] == '.')
00284             continue;
00285 
00286         list[count] = (char *)G_malloc(strlen(dp->d_name) + 1);
00287         strcpy(list[count], dp->d_name);
00288         count++;
00289     }
00290     closedir(dirp);
00291 
00292     return list;
00293 }
00294 
00302 void G_free_list(char **list)
00303 {
00304     int i = 0;
00305 
00306     if (!list)
00307         return;
00308 
00309     while (list[i]) {
00310         G_free(list[i]);
00311         i++;
00312     }
00313     G_free(list);
00314 }

Generated on Thu Dec 9 2010 20:46:05 for GRASS Programmer's Manual by  doxygen 1.7.2