Fork us on GitHub Follow us on Facebook Follow us on Twitter

Changeset 415c7e0d in mainline


Ignore:
Timestamp:
2009-06-28T21:41:13Z (12 years ago)
Author:
Jakub Jermar <jakub@…>
Branches:
lfn, master
Children:
bfd247f
Parents:
75160a6
Message:

Implement stat() and VFS_IN_STAT.
Modify bdsh() to use stat() during ls.
In devfs, allow lookups that don't
specify one of L_FILE and L_DIRECTORY.

Location:
uspace
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • uspace/app/bdsh/cmds/modules/ls/ls.c

    r75160a6 r415c7e0d  
    5151static char *cmdname = "ls";
    5252
    53 static inline off_t flen(const char *f)
    54 {
    55         int fd;
    56         off_t size;
    57 
    58         fd = open(f, O_RDONLY);
    59         if (fd == -1)
    60                 return 0;
    61 
    62         size = lseek(fd, 0, SEEK_END);
    63         close(fd);
    64 
    65         if (size < 0)
    66                 size = 0;
    67 
    68         return size;
    69 }
    70 
    71 static unsigned int ls_scope(const char *path)
    72 {
    73         int fd;
    74         DIR *dirp;
    75 
    76         dirp = opendir(path);
    77         if (dirp) {
    78                 closedir(dirp);
    79                 return LS_DIR;
    80         }
    81 
    82         fd = open(path, O_RDONLY);
    83         if (fd > 0) {
    84                 close(fd);
    85                 return LS_FILE;
    86         }
    87 
    88         return LS_BOGUS;
    89 }
    90 
    9153static void ls_scan_dir(const char *d, DIR *dirp)
    9254{
    9355        struct dirent *dp;
    94         unsigned int scope;
    9556        char *buff;
    9657
     
    10970                 * absolutize() later with subsequent calls to open() or readdir() */
    11071                snprintf(buff, PATH_MAX - 1, "%s/%s", d, dp->d_name);
    111                 scope = ls_scope(buff);
    112                 switch (scope) {
    113                 case LS_DIR:
    114                         ls_print_dir(dp->d_name);
    115                         break;
    116                 case LS_FILE:
    117                         ls_print_file(dp->d_name, buff);
    118                         break;
    119                 case LS_BOGUS:
    120                         /* Odd chance it was deleted from the time readdir() found
    121                          * it and the time that it was scoped */
    122                         printf("ls: skipping bogus node %s\n", dp->d_name);
    123                         break;
    124                 }
     72                ls_print(dp->d_name, buff);
    12573        }
    12674
     
    13078}
    13179
    132 /* ls_print_* currently does nothing more than print the entry.
     80/* ls_print currently does nothing more than print the entry.
    13381 * in the future, we will likely pass the absolute path, and
    13482 * some sort of ls_options structure that controls how each
     
    13785 * Now we just print basic DOS style lists */
    13886
    139 static void ls_print_dir(const char *d)
     87static void ls_print(const char *name, const char *pathname)
    14088{
    141         printf("%-40s\t<dir>\n", d);
     89        struct stat s;
     90        int rc;
    14291
    143         return;
    144 }
    145 
    146 static void ls_print_file(const char *name, const char *pathname)
    147 {
    148         printf("%-40s\t%llu\n", name, (long long) flen(pathname));
     92        if (rc = stat(pathname, &s)) {
     93                /* Odd chance it was deleted from the time readdir() found it */
     94                printf("ls: skipping bogus node %s\n", pathname);
     95                printf("rc=%d\n", rc);
     96                return;
     97        }
     98       
     99        if (s.is_file)
     100                printf("%-40s\t%llu\n", name, (long long) s.size);
     101        else
     102                printf("%-40s\n", name);
    149103
    150104        return;
     
    167121{
    168122        unsigned int argc;
    169         unsigned int scope;
     123        struct stat s;
    170124        char *buff;
    171125        DIR *dirp;
     
    185139                str_cpy(buff, PATH_MAX, argv[1]);
    186140
    187         scope = ls_scope(buff);
    188 
    189         switch (scope) {
    190         case LS_BOGUS:
     141        if (stat(buff, &s)) {
    191142                cli_error(CL_ENOENT, buff);
    192143                free(buff);
    193144                return CMD_FAILURE;
    194         case LS_FILE:
    195                 ls_print_file(buff, buff);
    196                 break;
    197         case LS_DIR:
     145        }
     146
     147        if (s.is_file) {
     148                ls_print(buff, buff);
     149        } else {
    198150                dirp = opendir(buff);
    199                 if (! dirp) {
     151                if (!dirp) {
    200152                        /* May have been deleted between scoping it and opening it */
    201153                        cli_error(CL_EFAIL, "Could not stat %s", buff);
     
    205157                ls_scan_dir(buff, dirp);
    206158                closedir(dirp);
    207                 break;
    208159        }
    209160
  • uspace/app/bdsh/cmds/modules/ls/ls.h

    r75160a6 r415c7e0d  
    1010static unsigned int ls_scope(const char *);
    1111static void ls_scan_dir(const char *, DIR *);
    12 static void ls_print_dir(const char *);
    13 static void ls_print_file(const char *, const char *);
     12static void ls_print(const char *, const char *);
    1413
    1514#endif /* LS_H */
  • uspace/lib/libc/generic/vfs/vfs.c

    r75160a6 r415c7e0d  
    389389}
    390390
     391int stat(const char *path, struct stat *stat)
     392{
     393        ipcarg_t rc;
     394        aid_t req;
     395       
     396        size_t pa_size;
     397        char *pa = absolutize(path, &pa_size);
     398        if (!pa)
     399                return ENOMEM;
     400       
     401        futex_down(&vfs_phone_futex);
     402        async_serialize_start();
     403        vfs_connect();
     404       
     405        req = async_send_0(vfs_phone, VFS_IN_STAT, NULL);
     406        rc = ipc_data_write_start(vfs_phone, pa, pa_size);
     407        if (rc != EOK) {
     408                async_wait_for(req, NULL);
     409                async_serialize_end();
     410                futex_up(&vfs_phone_futex);
     411                free(pa);
     412                return (int) rc;
     413        }
     414        rc = ipc_data_read_start(vfs_phone, stat, sizeof(struct stat));
     415        if (rc != EOK) {
     416                async_wait_for(req, NULL);
     417                async_serialize_end();
     418                futex_up(&vfs_phone_futex);
     419                free(pa);
     420                return (int) rc;
     421        }
     422        async_wait_for(req, &rc);
     423        async_serialize_end();
     424        futex_up(&vfs_phone_futex);
     425        free(pa);
     426        return rc;
     427}
     428
    391429DIR *opendir(const char *dirname)
    392430{
  • uspace/lib/libc/include/sys/stat.h

    r75160a6 r415c7e0d  
    5656
    5757extern int fstat(int, struct stat *);
     58extern int stat(const char *, struct stat *);
    5859extern int mkdir(const char *, mode_t);
    5960
  • uspace/srv/fs/devfs/devfs_ops.c

    r75160a6 r415c7e0d  
    165165        if (first >= last) {
    166166                /* Root entry */
    167                 if (lflag & L_DIRECTORY)
     167                if (!(lflag & L_FILE))
    168168                        ipc_answer_5(rid, EOK, devfs_reg.fs_handle, dev_handle, 0, 0, 0);
    169169                else
    170170                        ipc_answer_0(rid, ENOENT);
    171171        } else {
    172                 if (lflag & L_FILE) {
     172                if (!(lflag & L_DIRECTORY)) {
    173173                        size_t len;
    174174                        if (last >= first)
  • uspace/srv/vfs/vfs_ops.c

    r75160a6 r415c7e0d  
    964964void vfs_stat(ipc_callid_t rid, ipc_call_t *request)
    965965{
     966        size_t len;
     967        ipc_callid_t callid;
     968
     969        if (!ipc_data_write_receive(&callid, &len)) {
     970                ipc_answer_0(callid, EINVAL);
     971                ipc_answer_0(rid, EINVAL);
     972                return;
     973        }
     974        char *path = malloc(len + 1);
     975        if (!path) {
     976                ipc_answer_0(callid, ENOMEM);
     977                ipc_answer_0(rid, ENOMEM);
     978                return;
     979        }
     980        int rc;
     981        if ((rc = ipc_data_write_finalize(callid, path, len))) {
     982                ipc_answer_0(rid, rc);
     983                free(path);
     984                return;
     985        }
     986        path[len] = '\0';
     987
     988        if (!ipc_data_read_receive(&callid, NULL)) {
     989                free(path);
     990                ipc_answer_0(callid, EINVAL);
     991                ipc_answer_0(rid, EINVAL);
     992                return;
     993        }
     994
     995        vfs_lookup_res_t lr;
     996        fibril_rwlock_read_lock(&namespace_rwlock);
     997        rc = vfs_lookup_internal(path, L_NONE, &lr, NULL);
     998        free(path);
     999        if (rc != EOK) {
     1000                fibril_rwlock_read_unlock(&namespace_rwlock);
     1001                ipc_answer_0(callid, rc);
     1002                ipc_answer_0(rid, rc);
     1003                return;
     1004        }
     1005        vfs_node_t *node = vfs_node_get(&lr);
     1006        if (!node) {
     1007                fibril_rwlock_read_unlock(&namespace_rwlock);
     1008                ipc_answer_0(callid, ENOMEM);
     1009                ipc_answer_0(rid, ENOMEM);
     1010                return;
     1011        }
     1012
     1013        fibril_rwlock_read_unlock(&namespace_rwlock);
     1014
     1015        int fs_phone = vfs_grab_phone(node->fs_handle);
     1016        aid_t msg;
     1017        msg = async_send_3(fs_phone, VFS_OUT_STAT, node->dev_handle,
     1018            node->index, false, NULL);
     1019        ipc_forward_fast(callid, fs_phone, 0, 0, 0, IPC_FF_ROUTE_FROM_ME);
     1020        async_wait_for(msg, &rc);
     1021        vfs_release_phone(fs_phone);
     1022
     1023        ipc_answer_0(rid, rc);
     1024
     1025        vfs_node_put(node);
    9661026}
    9671027
Note: See TracChangeset for help on using the changeset viewer.