1 1.5 christos /* $NetBSD: ls.c,v 1.5 2014/03/20 03:13:18 christos Exp $ */ 2 1.3 tsutsui 3 1.1 brezak /*- 4 1.3 tsutsui * Copyright (c) 2011 5 1.3 tsutsui * The NetBSD Foundation, Inc. All rights reserved. 6 1.3 tsutsui * 7 1.3 tsutsui * This code is derived from software contributed to The NetBSD Foundation 8 1.3 tsutsui * by Martin Husemann. 9 1.3 tsutsui * 10 1.3 tsutsui * Redistribution and use in source and binary forms, with or without 11 1.3 tsutsui * modification, are permitted provided that the following conditions 12 1.3 tsutsui * are met: 13 1.3 tsutsui * 1. Redistributions of source code must retain the above copyright 14 1.3 tsutsui * notice, this list of conditions and the following disclaimer. 15 1.3 tsutsui * 2. Redistributions in binary form must reproduce the above copyright 16 1.3 tsutsui * notice, this list of conditions and the following disclaimer in the 17 1.3 tsutsui * documentation and/or other materials provided with the distribution. 18 1.3 tsutsui * 19 1.3 tsutsui * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 1.3 tsutsui * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 1.3 tsutsui * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 1.3 tsutsui * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 1.3 tsutsui * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 1.3 tsutsui * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 1.3 tsutsui * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 1.3 tsutsui * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 1.3 tsutsui * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 1.3 tsutsui * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 1.3 tsutsui * POSSIBILITY OF SUCH DAMAGE. 30 1.3 tsutsui */ 31 1.3 tsutsui 32 1.3 tsutsui /* 33 1.1 brezak * Copyright (c) 1993 34 1.1 brezak * The Regents of the University of California. All rights reserved. 35 1.1 brezak * 36 1.1 brezak * Redistribution and use in source and binary forms, with or without 37 1.1 brezak * modification, are permitted provided that the following conditions 38 1.1 brezak * are met: 39 1.1 brezak * 1. Redistributions of source code must retain the above copyright 40 1.1 brezak * notice, this list of conditions and the following disclaimer. 41 1.1 brezak * 2. Redistributions in binary form must reproduce the above copyright 42 1.1 brezak * notice, this list of conditions and the following disclaimer in the 43 1.1 brezak * documentation and/or other materials provided with the distribution. 44 1.3 tsutsui * 3. Neither the name of the University nor the names of its contributors 45 1.1 brezak * may be used to endorse or promote products derived from this software 46 1.1 brezak * without specific prior written permission. 47 1.1 brezak * 48 1.1 brezak * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 49 1.1 brezak * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 50 1.1 brezak * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 51 1.1 brezak * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 52 1.1 brezak * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 53 1.1 brezak * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 54 1.1 brezak * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 55 1.1 brezak * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 56 1.1 brezak * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 57 1.1 brezak * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 58 1.1 brezak * SUCH DAMAGE. 59 1.1 brezak */ 60 1.1 brezak 61 1.3 tsutsui /* 62 1.3 tsutsui * Copyright (c) 1996 63 1.3 tsutsui * Matthias Drochner. All rights reserved. 64 1.3 tsutsui * 65 1.3 tsutsui * Redistribution and use in source and binary forms, with or without 66 1.3 tsutsui * modification, are permitted provided that the following conditions 67 1.3 tsutsui * are met: 68 1.3 tsutsui * 1. Redistributions of source code must retain the above copyright 69 1.3 tsutsui * notice, this list of conditions and the following disclaimer. 70 1.3 tsutsui * 2. Redistributions in binary form must reproduce the above copyright 71 1.3 tsutsui * notice, this list of conditions and the following disclaimer in the 72 1.3 tsutsui * documentation and/or other materials provided with the distribution. 73 1.3 tsutsui * 74 1.3 tsutsui * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 75 1.3 tsutsui * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 76 1.3 tsutsui * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 77 1.3 tsutsui * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 78 1.3 tsutsui * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 79 1.3 tsutsui * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 80 1.3 tsutsui * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 81 1.3 tsutsui * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 82 1.3 tsutsui * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 83 1.3 tsutsui * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 84 1.3 tsutsui */ 85 1.3 tsutsui 86 1.3 tsutsui 87 1.1 brezak #include "stand.h" 88 1.5 christos #include "ls.h" 89 1.3 tsutsui #include <sys/stat.h> 90 1.3 tsutsui #include <lib/libkern/libkern.h> 91 1.1 brezak 92 1.3 tsutsui void 93 1.3 tsutsui ls(const char *path) 94 1.1 brezak { 95 1.3 tsutsui int fd; 96 1.3 tsutsui struct stat sb; 97 1.3 tsutsui size_t size; 98 1.3 tsutsui const char *fname = 0; 99 1.3 tsutsui char *p; 100 1.3 tsutsui struct open_file *f; 101 1.3 tsutsui 102 1.3 tsutsui if ((fd = open(path, 0)) < 0 103 1.3 tsutsui || fstat(fd, &sb) < 0 104 1.3 tsutsui || (sb.st_mode & S_IFMT) != S_IFDIR) { 105 1.3 tsutsui /* Path supplied isn't a directory, open parent 106 1.3 tsutsui directory and list matching files. */ 107 1.3 tsutsui if (fd >= 0) 108 1.3 tsutsui close(fd); 109 1.3 tsutsui fname = strrchr(path, '/'); 110 1.3 tsutsui if (fname) { 111 1.3 tsutsui size = fname - path; 112 1.4 tsutsui fname++; 113 1.3 tsutsui p = alloc(size + 1); 114 1.3 tsutsui if (!p) 115 1.3 tsutsui goto out; 116 1.3 tsutsui memcpy(p, path, size); 117 1.3 tsutsui p[size] = 0; 118 1.3 tsutsui fd = open(p, 0); 119 1.3 tsutsui dealloc(p, size + 1); 120 1.3 tsutsui } else { 121 1.3 tsutsui fd = open("", 0); 122 1.3 tsutsui fname = path; 123 1.3 tsutsui } 124 1.1 brezak 125 1.3 tsutsui if (fd < 0) { 126 1.3 tsutsui printf("ls: %s\n", strerror(errno)); 127 1.3 tsutsui return; 128 1.1 brezak } 129 1.3 tsutsui if (fstat(fd, &sb) < 0) { 130 1.3 tsutsui printf("stat: %s\n", strerror(errno)); 131 1.3 tsutsui goto out; 132 1.3 tsutsui } 133 1.3 tsutsui if ((sb.st_mode & S_IFMT) != S_IFDIR) { 134 1.3 tsutsui printf("%s: %s\n", path, strerror(ENOTDIR)); 135 1.3 tsutsui goto out; 136 1.1 brezak } 137 1.1 brezak } 138 1.1 brezak 139 1.3 tsutsui f = &files[fd]; 140 1.1 brezak 141 1.3 tsutsui #if !defined(LIBSA_NO_FD_CHECKING) 142 1.3 tsutsui if ((unsigned int)fd >= SOPEN_MAX || f->f_flags == 0) { 143 1.3 tsutsui errno = EBADF; 144 1.3 tsutsui goto out; 145 1.3 tsutsui } 146 1.3 tsutsui #endif 147 1.3 tsutsui 148 1.3 tsutsui #if !defined(LIBSA_NO_RAW_ACCESS) 149 1.3 tsutsui /* operation not defined on raw devices */ 150 1.3 tsutsui if (f->f_flags & F_RAW) { 151 1.3 tsutsui errno = EOPNOTSUPP; 152 1.3 tsutsui goto out; 153 1.3 tsutsui } 154 1.3 tsutsui #endif 155 1.1 brezak 156 1.3 tsutsui if (FS_LS(f->f_ops) != NULL) 157 1.3 tsutsui FS_LS(f->f_ops)(f, fname); 158 1.3 tsutsui else 159 1.3 tsutsui printf("no ls support for this file system\n"); 160 1.1 brezak 161 1.3 tsutsui out: 162 1.3 tsutsui close(fd); 163 1.1 brezak } 164 1.5 christos 165 1.5 christos struct lsentry { 166 1.5 christos struct lsentry *e_next; 167 1.5 christos uint32_t e_ino; 168 1.5 christos const char *e_type; 169 1.5 christos char e_name[1]; 170 1.5 christos }; 171 1.5 christos 172 1.5 christos __compactcall void 173 1.5 christos lsadd(lsentry_t **names, const char *pattern, const char *name, size_t namelen, 174 1.5 christos uint32_t ino, const char *type) 175 1.5 christos { 176 1.5 christos lsentry_t *n, **np; 177 1.5 christos 178 1.5 christos if (pattern && !fnmatch(name, pattern)) 179 1.5 christos return; 180 1.5 christos 181 1.5 christos n = alloc(sizeof *n + namelen); 182 1.5 christos if (!n) { 183 1.5 christos printf("%d: %.*s (%s)\n", ino, (int)namelen, name, type); 184 1.5 christos return; 185 1.5 christos } 186 1.5 christos 187 1.5 christos n->e_ino = ino; 188 1.5 christos n->e_type = type; 189 1.5 christos memcpy(n->e_name, name, namelen); 190 1.5 christos n->e_name[namelen] = '\0'; 191 1.5 christos 192 1.5 christos for (np = names; *np; np = &(*np)->e_next) { 193 1.5 christos if (strcmp(n->e_name, (*np)->e_name) < 0) 194 1.5 christos break; 195 1.5 christos } 196 1.5 christos n->e_next = *np; 197 1.5 christos *np = n; 198 1.5 christos } 199 1.5 christos 200 1.5 christos __compactcall void 201 1.5 christos lsprint(lsentry_t *names) { 202 1.5 christos if (!names) { 203 1.5 christos printf("not found\n"); 204 1.5 christos return; 205 1.5 christos } 206 1.5 christos do { 207 1.5 christos lsentry_t *n = names; 208 1.5 christos printf("%d: %s (%s)\n", n->e_ino, n->e_name, n->e_type); 209 1.5 christos names = n->e_next; 210 1.5 christos } while (names); 211 1.5 christos } 212 1.5 christos 213 1.5 christos __compactcall void 214 1.5 christos lsfree(lsentry_t *names) { 215 1.5 christos if (!names) 216 1.5 christos return; 217 1.5 christos do { 218 1.5 christos lsentry_t *n = names; 219 1.5 christos names = n->e_next; 220 1.5 christos dealloc(n, 0); 221 1.5 christos } while (names); 222 1.5 christos } 223 1.5 christos 224 1.5 christos __compactcall void 225 1.5 christos lsunsup(const char *name) { 226 1.5 christos printf("The ls command is not currently supported for %s\n", name); 227 1.5 christos } 228