The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/fs/nwfs/nwfs_subr.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*-
    2  * Copyright (c) 1999, 2001 Boris Popov
    3  * All rights reserved.
    4  *
    5  * Redistribution and use in source and binary forms, with or without
    6  * modification, are permitted provided that the following conditions
    7  * are met:
    8  * 1. Redistributions of source code must retain the above copyright
    9  *    notice, this list of conditions and the following disclaimer.
   10  * 2. Redistributions in binary form must reproduce the above copyright
   11  *    notice, this list of conditions and the following disclaimer in the
   12  *    documentation and/or other materials provided with the distribution.
   13  *
   14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
   15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
   16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
   17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
   18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
   19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
   20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
   22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
   23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   24  * SUCH DAMAGE.
   25  *
   26  * $FreeBSD$
   27  */
   28 #include <sys/param.h>
   29 #include <sys/systm.h>
   30 #include <sys/kernel.h>
   31 #include <sys/lock.h>
   32 #include <sys/lockmgr.h>
   33 #include <sys/malloc.h>
   34 #include <sys/clock.h>
   35 #include <sys/time.h>
   36 
   37 #include <netncp/ncp.h>
   38 #include <netncp/ncp_conn.h>
   39 #include <netncp/ncp_ncp.h>
   40 #include <netncp/ncp_subr.h>
   41 #include <netncp/ncp_rq.h>
   42 #include <netncp/nwerror.h>
   43 
   44 #include <fs/nwfs/nwfs.h>
   45 #include <fs/nwfs/nwfs_node.h>
   46 #include <fs/nwfs/nwfs_subr.h>
   47 
   48 #define NCP_INFOSZ      (sizeof(struct nw_entry_info) - 257)
   49 
   50 MALLOC_DEFINE(M_NWFSDATA, "nwfs_data", "NWFS private data");
   51 
   52 static int
   53 ncp_extract_file_info(struct nwmount *nmp, struct ncp_rq *rqp,
   54         struct nw_entry_info *target, int withname)
   55 {
   56         u_int8_t name_len;
   57 
   58         md_get_mem(&rqp->rp, (caddr_t)target, NCP_INFOSZ, MB_MSYSTEM);
   59         if (!withname)
   60                 return 0;
   61         md_get_uint8(&rqp->rp, &name_len);
   62         target->nameLen = name_len;
   63         md_get_mem(&rqp->rp, (caddr_t)target->entryName, name_len, MB_MSYSTEM);
   64         target->entryName[name_len] = '\0';
   65         ncp_path2unix(target->entryName, target->entryName, name_len, &nmp->m.nls);
   66         return 0;
   67 }
   68 
   69 int
   70 ncp_initsearch(struct vnode *dvp, struct thread *td, struct ucred *cred)
   71 {
   72         struct nwmount *nmp = VTONWFS(dvp);
   73         struct ncp_conn *conn = NWFSTOCONN(nmp);
   74         struct nwnode *np = VTONW(dvp);
   75         struct ncp_rq *rqp;
   76         u_int8_t volnum = nmp->n_volume;
   77         u_int32_t dirent = np->n_fid.f_id;
   78         int error;
   79 
   80         NCPNDEBUG("vol=%d,dir=%d\n", volnum, dirent);
   81         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
   82         if (error)
   83                 return error;
   84         mb_put_uint8(&rqp->rq, 2);              /* subfunction */
   85         mb_put_uint8(&rqp->rq, nmp->name_space);
   86         mb_put_uint8(&rqp->rq, 0);              /* reserved */
   87         ncp_rq_dbase_path(rqp, volnum, dirent, 0, NULL, NULL);
   88         rqp->nr_minrplen = sizeof(np->n_seq);
   89         error = ncp_request(rqp);
   90         if (error)
   91                 return error;
   92         md_get_mem(&rqp->rp, (caddr_t)&np->n_seq, sizeof(np->n_seq), MB_MSYSTEM);
   93         ncp_rq_done(rqp);
   94         return 0;
   95 }
   96 
   97 int 
   98 ncp_search_for_file_or_subdir(struct nwmount *nmp,
   99                               struct nw_search_seq *seq,
  100                               struct nw_entry_info *target,
  101                               struct thread *td,struct ucred *cred)
  102 {
  103         struct ncp_conn *conn = NWFSTOCONN(nmp);
  104         struct ncp_rq *rqp;
  105         int error;
  106 
  107         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  108         if (error)
  109                 return error;
  110         mb_put_uint8(&rqp->rq, 3);              /* subfunction */
  111         mb_put_uint8(&rqp->rq, nmp->name_space);
  112         mb_put_uint8(&rqp->rq, 0);              /* data stream */
  113         mb_put_uint16le(&rqp->rq, 0xffff);      /* Search attribs */
  114         mb_put_uint32le(&rqp->rq, IM_ALL);      /* return info mask */
  115         mb_put_mem(&rqp->rq, (caddr_t)seq, 9, MB_MSYSTEM);
  116         mb_put_uint8(&rqp->rq, 2);              /* 2 byte pattern */
  117         mb_put_uint8(&rqp->rq, 0xff);           /* following is a wildcard */
  118         mb_put_uint8(&rqp->rq, '*');
  119         rqp->nr_minrplen = sizeof(*seq) +  1 + NCP_INFOSZ + 1;
  120         error = ncp_request(rqp);
  121         if (error)
  122                 return error;
  123         md_get_mem(&rqp->rp, (caddr_t)seq, sizeof(*seq), MB_MSYSTEM);
  124         md_get_uint8(&rqp->rp, NULL);           /* skip */
  125         error = ncp_extract_file_info(nmp, rqp, target, 1);
  126         ncp_rq_done(rqp);
  127         return error;
  128 }
  129 
  130 /*
  131  * Returns information for a (one-component) name relative to the specified
  132  * directory.
  133  */
  134 int 
  135 ncp_obtain_info(struct nwmount *nmp,  u_int32_t dirent,
  136                 int namelen, char *path, struct nw_entry_info *target,
  137                 struct thread *td,struct ucred *cred)
  138 {
  139         struct ncp_conn *conn=NWFSTOCONN(nmp);
  140         struct ncp_rq *rqp;
  141         int error;
  142         u_char volnum = nmp->n_volume, ns;
  143 
  144         if (target == NULL) {
  145                 NCPFATAL("target == NULL\n");
  146                 return EINVAL;
  147         }
  148         ns = (path == NULL || path[0] == 0) ? NW_NS_DOS : nmp->name_space;
  149         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  150         if (error)
  151                 return error;
  152         mb_put_uint8(&rqp->rq, 6);      /* subfunction */
  153         mb_put_uint8(&rqp->rq, ns);
  154         mb_put_uint8(&rqp->rq, ns);     /* DestNameSpace */
  155         mb_put_uint16le(&rqp->rq, 0xff);        /* get all */
  156         mb_put_uint32le(&rqp->rq, IM_ALL);
  157         ncp_rq_dbase_path(rqp, volnum, dirent, namelen, path, &nmp->m.nls);
  158         error = ncp_request(rqp);
  159         if (error)
  160                 return error;
  161         error = ncp_extract_file_info(nmp, rqp, target, path != NULL);
  162         ncp_rq_done(rqp);
  163         return error;
  164 }
  165 /* 
  166  * lookup name pointed by cnp in directory dvp and return file info in np.
  167  * May be I should create a little cache, but another way is to minimize
  168  * number of calls, on other hand, in multiprocess environment ...
  169  */
  170 int
  171 ncp_lookup(struct vnode *dvp, int len, char *name, struct nw_entry_info *fap,
  172                 struct thread *td,struct ucred *cred)
  173 {
  174         struct nwmount *nmp;
  175         struct nwnode *dnp;
  176         int error;
  177 
  178         if (!dvp || dvp->v_type != VDIR) {
  179                 nwfs_printf("dvp is NULL or not a directory.\n");
  180                 return (ENOENT);
  181         }
  182         dnp = VTONW(dvp);
  183         nmp = VTONWFS(dvp);
  184 
  185         if (len == 1 && name[0] == '.') {
  186                 if (dnp->n_flag & NVOLUME) {
  187                         error = ncp_obtain_info(nmp, dnp->n_fid.f_id, 0, NULL,
  188                                 fap, td, cred);
  189                 } else {
  190                         error = ncp_obtain_info(nmp, dnp->n_fid.f_parent, 
  191                                 dnp->n_nmlen, dnp->n_name, fap, td, cred);
  192                 }
  193                 return error;
  194         } else if (len == 2 && name[0] == '.' && name[1] == '.') {
  195                 printf("%s: knows NOTHING about '..'\n", __func__);
  196                 return EIO;
  197         } else {
  198                 error = ncp_obtain_info(nmp, dnp->n_fid.f_id, 
  199                         len, name, fap, td, cred);
  200         }
  201         return error;
  202 }
  203 
  204 static void ConvertToNWfromDWORD(u_int32_t sfd, ncp_fh *fh);
  205 static void 
  206 ConvertToNWfromDWORD(u_int32_t sfd, ncp_fh *fh) {
  207         fh->val1 = (fh->val.val32 = sfd);
  208         return;
  209 }
  210 
  211 /*
  212  * If both dir and name are NULL, then in target there's already a looked-up
  213  * entry that wants to be opened.
  214  */
  215 int 
  216 ncp_open_create_file_or_subdir(struct nwmount *nmp,struct vnode *dvp,int namelen,
  217             char *name, int open_create_mode, u_int32_t create_attributes,
  218             int desired_acc_rights, struct ncp_open_info *nop,
  219             struct thread *td,struct ucred *cred)
  220 {
  221         
  222         struct ncp_conn *conn=NWFSTOCONN(nmp);
  223         struct ncp_rq *rqp;
  224         u_int16_t search_attribs = SA_ALL & (~SA_SUBDIR_FILES);
  225         u_int8_t volnum;
  226         u_int32_t dirent;
  227         int error;
  228 
  229         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  230         if (error)
  231                 return error;
  232         volnum = nmp->n_volume;
  233         dirent = VTONW(dvp)->n_fid.f_id;
  234         if ((create_attributes & aDIR) != 0) {
  235                 search_attribs |= SA_SUBDIR_FILES;
  236         }
  237         mb_put_uint8(&rqp->rq, 1);/* subfunction */
  238         mb_put_uint8(&rqp->rq, nmp->name_space);
  239         mb_put_uint8(&rqp->rq, open_create_mode);
  240         mb_put_uint16le(&rqp->rq, search_attribs);
  241         mb_put_uint32le(&rqp->rq, IM_ALL);
  242         mb_put_uint32le(&rqp->rq, create_attributes);
  243         /*
  244          * The desired acc rights seem to be the inherited rights mask for
  245          * directories
  246          */
  247         mb_put_uint16le(&rqp->rq, desired_acc_rights);
  248         ncp_rq_dbase_path(rqp, volnum, dirent, namelen, name, &nmp->m.nls);
  249         error = ncp_request(rqp);
  250         if (error) {
  251                 if (error == NWE_FILE_NO_CREATE_PRIV)
  252                         error = EACCES;
  253                 return error;
  254         }
  255         md_get_uint32le(&rqp->rp, &nop->origfh);
  256         md_get_uint8(&rqp->rp, &nop->action);
  257         md_get_uint8(&rqp->rp, NULL);   /* skip */
  258         error = ncp_extract_file_info(nmp, rqp, &nop->fattr, 1);
  259         ncp_rq_done(rqp);
  260         ConvertToNWfromDWORD(nop->origfh, &nop->fh);
  261         return error;
  262 }
  263 
  264 int
  265 ncp_close_file(struct ncp_conn *conn, ncp_fh *fh,struct thread *td,struct ucred *cred)
  266 {
  267         struct ncp_rq *rqp;
  268         int error;
  269 
  270         error = ncp_rq_alloc(66, conn, td, cred, &rqp);
  271         if (error)
  272                 return error;
  273         mb_put_uint8(&rqp->rq, 0);
  274         mb_put_mem(&rqp->rq, (caddr_t)fh, 6, MB_MSYSTEM);
  275         error = ncp_request(rqp);
  276         if (error)
  277                 return error;
  278         ncp_rq_done(rqp);
  279         return error;
  280 }
  281 
  282 int
  283 ncp_DeleteNSEntry(struct nwmount *nmp, u_int32_t dirent,
  284         int namelen,char *name,struct thread *td,struct ucred *cred)
  285 {
  286         struct ncp_rq *rqp;
  287         int error;
  288         struct ncp_conn *conn=NWFSTOCONN(nmp);
  289 
  290         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  291         if (error)
  292                 return error;
  293         mb_put_uint8(&rqp->rq, 8);              /* subfunction */
  294         mb_put_uint8(&rqp->rq, nmp->name_space);
  295         mb_put_uint8(&rqp->rq, 0);              /* reserved */
  296         mb_put_uint16le(&rqp->rq, SA_ALL);      /* search attribs: all */
  297         ncp_rq_dbase_path(rqp, nmp->n_volume, dirent, namelen, name, &nmp->m.nls);
  298         error = ncp_request(rqp);
  299         if (!error)
  300                 ncp_rq_done(rqp);
  301         return error;
  302 }
  303 
  304 int 
  305 ncp_nsrename(struct ncp_conn *conn, int volume, int ns, int oldtype, 
  306         struct ncp_nlstables *nt,
  307         nwdirent fdir, char *old_name, int oldlen,
  308         nwdirent tdir, char *new_name, int newlen,
  309         struct thread *td, struct ucred *cred)
  310 {
  311         struct ncp_rq *rqp;
  312         int error;
  313 
  314         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  315         if (error)
  316                 return error;
  317         mb_put_uint8(&rqp->rq, 4);
  318         mb_put_uint8(&rqp->rq, ns);
  319         mb_put_uint8(&rqp->rq, 1);      /* RRenameToMySelf */
  320         mb_put_uint16le(&rqp->rq, oldtype);
  321         /* source Handle Path */
  322         mb_put_uint8(&rqp->rq, volume);
  323         mb_put_mem(&rqp->rq, (c_caddr_t)&fdir, sizeof(fdir), MB_MSYSTEM);
  324         mb_put_uint8(&rqp->rq, 1);
  325         mb_put_uint8(&rqp->rq, 1);      /* 1 source component */
  326         /* dest Handle Path */
  327         mb_put_uint8(&rqp->rq, volume);
  328         mb_put_mem(&rqp->rq, (c_caddr_t)&tdir, sizeof(tdir), MB_MSYSTEM);
  329         mb_put_uint8(&rqp->rq, 1);
  330         mb_put_uint8(&rqp->rq, 1);      /* 1 destination component */
  331         ncp_rq_pathstring(rqp, oldlen, old_name, nt);
  332         ncp_rq_pathstring(rqp, newlen, new_name, nt);
  333         error = ncp_request(rqp);
  334         if (!error)
  335                 ncp_rq_done(rqp);
  336         return error;
  337 }
  338 
  339 int
  340 ncp_modify_file_or_subdir_dos_info(struct nwmount *nmp, struct vnode *vp, 
  341                                 u_int32_t info_mask,
  342                                 struct nw_modify_dos_info *info,
  343                                 struct thread *td,struct ucred *cred)
  344 {
  345         struct nwnode *np=VTONW(vp);
  346         struct ncp_rq *rqp;
  347         u_int8_t volnum = nmp->n_volume;
  348         u_int32_t dirent = np->n_fid.f_id;
  349         struct ncp_conn *conn=NWFSTOCONN(nmp);
  350         int             error;
  351 
  352         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  353         if (error)
  354                 return error;
  355         mb_put_uint8(&rqp->rq, 7);      /* subfunction */
  356         mb_put_uint8(&rqp->rq, nmp->name_space);
  357         mb_put_uint8(&rqp->rq, 0);      /* reserved */
  358         mb_put_uint16le(&rqp->rq, SA_ALL);      /* search attribs: all */
  359         mb_put_uint32le(&rqp->rq, info_mask);
  360         mb_put_mem(&rqp->rq, (caddr_t)info, sizeof(*info), MB_MSYSTEM);
  361         ncp_rq_dbase_path(rqp, volnum, dirent, 0, NULL, NULL);
  362         error = ncp_request(rqp);
  363         if (!error)
  364                 ncp_rq_done(rqp);
  365         return error;
  366 }
  367 
  368 int
  369 ncp_setattr(vp, vap, cred, td)
  370         struct vnode *vp;
  371         struct vattr *vap;
  372         struct ucred *cred;
  373         struct thread *td;
  374 {
  375         struct nwmount *nmp=VTONWFS(vp);
  376         struct nwnode *np=VTONW(vp);
  377         struct ncp_open_info nwn;
  378         struct ncp_conn *conn=NWFSTOCONN(nmp);
  379         struct nw_modify_dos_info info;
  380         struct ncp_rq *rqp;
  381         int error = 0, info_mask;
  382 
  383         if (vap->va_size != VNOVAL) {
  384                 error = ncp_open_create_file_or_subdir(nmp, vp, 0, NULL, OC_MODE_OPEN, 0,
  385                                                    AR_WRITE | AR_READ, &nwn,td,cred);
  386                 if (error)
  387                         return error;
  388                 error = ncp_rq_alloc(73, conn, td, cred, &rqp);
  389                 if (error) {
  390                         ncp_close_file(conn, &nwn.fh, td, cred);
  391                         return error;
  392                 }
  393                 mb_put_uint8(&rqp->rq, 0);
  394                 mb_put_mem(&rqp->rq, (caddr_t)&nwn.fh, 6, MB_MSYSTEM);
  395                 mb_put_uint32be(&rqp->rq, vap->va_size);
  396                 mb_put_uint16be(&rqp->rq, 0);
  397                 error = ncp_request(rqp);
  398                 np->n_vattr.va_size = np->n_size = vap->va_size;
  399                 if (!error)
  400                         ncp_rq_done(rqp);
  401                 ncp_close_file(conn, &nwn.fh, td, cred);
  402                 if (error)
  403                         return error;
  404         }
  405         info_mask = 0;
  406         bzero(&info, sizeof(info));
  407 
  408         if (vap->va_mtime.tv_sec != VNOVAL) {
  409                 info_mask |= (DM_MODIFY_TIME | DM_MODIFY_DATE);
  410                 ncp_unix2dostime(&vap->va_mtime, nmp->m.tz, &info.modifyDate, &info.modifyTime, NULL);
  411         }
  412         if (vap->va_atime.tv_sec != VNOVAL) {
  413                 info_mask |= (DM_LAST_ACCESS_DATE);
  414                 ncp_unix2dostime(&vap->va_atime, nmp->m.tz, &info.lastAccessDate, NULL, NULL);
  415         }
  416         if (info_mask) {
  417                 error = ncp_modify_file_or_subdir_dos_info(nmp, vp, info_mask, &info,td,cred);
  418         }
  419         return (error);
  420 }
  421 
  422 int
  423 ncp_get_volume_info_with_number(struct ncp_conn *conn, 
  424         int n, struct ncp_volume_info *target,
  425         struct thread *td,struct ucred *cred)
  426 {
  427         struct ncp_rq *rqp;
  428         u_int32_t tmp32;
  429         u_int8_t len;
  430         int error;
  431 
  432         error = ncp_rq_alloc_subfn(22, 44, conn, td, cred, &rqp);
  433         if (error)
  434                 return error;
  435         mb_put_uint8(&rqp->rq,n);
  436         error = ncp_request(rqp);
  437         if (error)
  438                 return error;
  439         md_get_uint32le(&rqp->rp, &target->total_blocks);
  440         md_get_uint32le(&rqp->rp, &target->free_blocks);
  441         md_get_uint32le(&rqp->rp, &target->purgeable_blocks);
  442         md_get_uint32le(&rqp->rp, &target->not_yet_purgeable_blocks);
  443         md_get_uint32le(&rqp->rp, &target->total_dir_entries);
  444         md_get_uint32le(&rqp->rp, &target->available_dir_entries);
  445         md_get_uint32le(&rqp->rp, &tmp32);
  446         md_get_uint8(&rqp->rp, &target->sectors_per_block);
  447         bzero(&target->volume_name, sizeof(target->volume_name));
  448         md_get_uint8(&rqp->rp, &len);
  449         if (len > NCP_VOLNAME_LEN) {
  450                 error = ENAMETOOLONG;
  451         } else {
  452                 md_get_mem(&rqp->rp, (caddr_t)&target->volume_name, len, MB_MSYSTEM);
  453         }
  454         ncp_rq_done(rqp);
  455         return error;
  456 }
  457 
  458 int
  459 ncp_get_namespaces(struct ncp_conn *conn, u_int32_t volume, int *nsf,
  460         struct thread *td,struct ucred *cred)
  461 {
  462         struct ncp_rq *rqp;
  463         int error;
  464         u_int8_t ns;
  465         u_int16_t nscnt;
  466 
  467         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  468         if (error)
  469                 return error;
  470         mb_put_uint8(&rqp->rq, 24);     /* Subfunction: Get Loaded Name Spaces */
  471         mb_put_uint16le(&rqp->rq, 0);   /* reserved */
  472         mb_put_uint8(&rqp->rq, volume);
  473         error = ncp_request(rqp);
  474         if (error)
  475                 return error;
  476         md_get_uint16le(&rqp->rp, &nscnt);
  477         *nsf = 0;
  478         while (nscnt-- > 0) {
  479                 md_get_uint8(&rqp->rp, &ns);
  480                 *nsf |= 1 << ns;
  481         }
  482         ncp_rq_done(rqp);
  483         return error;
  484 }
  485 
  486 int
  487 ncp_lookup_volume(struct ncp_conn *conn, char *volname, 
  488                 u_char *volNum, u_int32_t *dirEnt,
  489                 struct thread *td,struct ucred *cred)
  490 {
  491         struct ncp_rq *rqp;
  492         u_int32_t tmp32;
  493         int error;
  494 
  495         NCPNDEBUG("looking up vol %s\n", volname);
  496         error = ncp_rq_alloc(87, conn, td, cred, &rqp);
  497         if (error)
  498                 return error;
  499         mb_put_uint8(&rqp->rq, 22);     /* Subfunction: Generate dir handle */
  500         mb_put_uint8(&rqp->rq, 0);      /* src name space */
  501         mb_put_uint8(&rqp->rq, 0);      /* dst name space, always zero */
  502         mb_put_uint16le(&rqp->rq, 0);   /* dstNSIndicator (Jn) */
  503 
  504         mb_put_uint8(&rqp->rq, 0);      /* faked volume number */
  505         mb_put_uint32be(&rqp->rq, 0);   /* faked dir_base */
  506         mb_put_uint8(&rqp->rq, 0xff);   /* Don't have a dir_base */
  507         mb_put_uint8(&rqp->rq, 1);      /* 1 path component */
  508         ncp_rq_pstring(rqp, volname);
  509         error = ncp_request(rqp);
  510         if (error)
  511                 return error;
  512         md_get_uint32le(&rqp->rp, &tmp32);
  513         md_get_uint32le(&rqp->rp, dirEnt);
  514         md_get_uint8(&rqp->rp, volNum);
  515         ncp_rq_done(rqp);
  516         return error;
  517 }
  518 
  519 /*
  520  * XXX: I think the timezone in struct nwfs_args is truly bogus, especially
  521  * XXX: considering that nwfs_mount(8) picks this up from the kernel in
  522  * XXX: the first place.  Since I can't test this, I won't attempt to fix it.
  523  * XXX: /phk
  524  */
  525 
  526 void
  527 ncp_unix2dostime(tsp, tzoff, ddp, dtp, dhp)
  528         struct timespec *tsp;
  529         int tzoff;
  530         u_int16_t *ddp;
  531         u_int16_t *dtp;
  532         u_int8_t *dhp;
  533 {
  534         struct timespec t;
  535 
  536         t = *tsp;
  537         
  538         t.tv_sec = - tzoff * 60 - utc_offset();
  539         timespec2fattime(&t, 1, ddp, dtp, dhp);
  540 }
  541 
  542 void
  543 ncp_dos2unixtime(dd, dt, dh, tzoff, tsp)
  544         u_int dd;
  545         u_int dt;
  546         u_int dh;
  547         int tzoff;
  548         struct timespec *tsp;
  549 {
  550 
  551         fattime2timespec(dd, dt, dh, 1, tsp);
  552         tsp->tv_sec += tzoff * 60 + utc_offset();
  553 }

Cache object: b65d97f5af891e1c922fcb6f8321fe51


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.