1/* $NetBSD$ */ 2 3/* 4 * Copyright (C) 2004-2007 Internet Systems Consortium, Inc. ("ISC") 5 * Copyright (C) 2000, 2001 Internet Software Consortium. 6 * 7 * Permission to use, copy, modify, and/or distribute this software for any 8 * purpose with or without fee is hereby granted, provided that the above 9 * copyright notice and this permission notice appear in all copies. 10 * 11 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH 12 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY 13 * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT, 14 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM 15 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE 16 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 17 * PERFORMANCE OF THIS SOFTWARE. 18 */ 19 20/* Id: fsaccess.c,v 1.13 2007/06/19 23:47:18 tbox Exp */ 21 22#include <config.h> 23 24#include <sys/types.h> 25#include <sys/stat.h> 26 27#include <errno.h> 28 29#include "errno2result.h" 30 31/*! \file 32 * \brief 33 * The OS-independent part of the API is in lib/isc. 34 */ 35#include "../fsaccess.c" 36 37isc_result_t 38isc_fsaccess_set(const char *path, isc_fsaccess_t access) { 39 struct stat statb; 40 mode_t mode; 41 isc_boolean_t is_dir = ISC_FALSE; 42 isc_fsaccess_t bits; 43 isc_result_t result; 44 45 if (stat(path, &statb) != 0) 46 return (isc__errno2result(errno)); 47 48 if ((statb.st_mode & S_IFDIR) != 0) 49 is_dir = ISC_TRUE; 50 else if ((statb.st_mode & S_IFREG) == 0) 51 return (ISC_R_INVALIDFILE); 52 53 result = check_bad_bits(access, is_dir); 54 if (result != ISC_R_SUCCESS) 55 return (result); 56 57 /* 58 * Done with checking bad bits. Set mode_t. 59 */ 60 mode = 0; 61 62#define SET_AND_CLEAR1(modebit) \ 63 if ((access & bits) != 0) { \ 64 mode |= modebit; \ 65 access &= ~bits; \ 66 } 67#define SET_AND_CLEAR(user, group, other) \ 68 SET_AND_CLEAR1(user); \ 69 bits <<= STEP; \ 70 SET_AND_CLEAR1(group); \ 71 bits <<= STEP; \ 72 SET_AND_CLEAR1(other); 73 74 bits = ISC_FSACCESS_READ | ISC_FSACCESS_LISTDIRECTORY; 75 76 SET_AND_CLEAR(S_IRUSR, S_IRGRP, S_IROTH); 77 78 bits = ISC_FSACCESS_WRITE | 79 ISC_FSACCESS_CREATECHILD | 80 ISC_FSACCESS_DELETECHILD; 81 82 SET_AND_CLEAR(S_IWUSR, S_IWGRP, S_IWOTH); 83 84 bits = ISC_FSACCESS_EXECUTE | 85 ISC_FSACCESS_ACCESSCHILD; 86 87 SET_AND_CLEAR(S_IXUSR, S_IXGRP, S_IXOTH); 88 89 INSIST(access == 0); 90 91 if (chmod(path, mode) < 0) 92 return (isc__errno2result(errno)); 93 94 return (ISC_R_SUCCESS); 95} 96