File:  [Research Unix] / researchv10dc / cmd / icon / src / iconx / lrec.c
Revision 1.1.1.1 (vendor branch): download - view: text, annotated - select for diffs
Tue Apr 24 17:21:34 2018 UTC (8 years, 3 months ago) by root
Branches: belllabs, MAIN
CVS tags: researchv10, HEAD
researchv10 Dan Cross

/*
 * File: lrec.c
 *  Contents: field, mkrec
 */

#include "../h/rt.h"

/*
 * x.y - access field y of record x.
 */

LibDcl(field,2,".")
   {
   register word fnum;
   register struct b_record *rp;
   register struct descrip *dp;
   extern word *ftab, *records;

   DeRef(Arg1);
   /*
    * x must be a record and y must be a field number.
    */
   if (Qual(Arg1) || Arg1.dword != D_Record)
      runerr(107, &Arg1);

   /*
    * Map the field number into a field number for the record x.
    */
   rp = (struct b_record *) BlkLoc(Arg1);
   fnum = ftab[IntVal(Arg2) * *records + BlkLoc(rp->recdesc)->proc.recnum - 1];
   /*
    * If fnum < 0, x doesn't contain the specified field.
    */
   if (fnum < 0)
      runerr(207, &Arg1);

   /*
    * Return a pointer to the descriptor for the appropriate field.
    */
   dp = &rp->fields[fnum];
   Arg0.dword = D_Var + ((word *)dp - (word *)rp);
   BlkLoc(Arg0) = (union block *) dp;
   Return;
   }


/*
 * mkrec - create a record.
 */

LibDcl(mkrec,-1,"mkrec")
   {
   register int i;
   register struct b_proc *bp;
   register struct b_record *rp;
   extern struct b_record *alcrecd();

   /*
    * Be sure that call is from a procedure.
    */

   /*
    * Ensure space for the record to be created.
    */
   blkreq((uword)sizeof(struct b_record) +
         BlkLoc(Arg(0))->proc.nfields*sizeof(struct descrip));

   /*
    * Get a pointer to the record constructor procedure and allocate
    *  a record with the appropriate number of fields.
    */
   bp = (struct b_proc *) BlkLoc(Arg(0));
   rp = alcrecd((int)bp->nfields, (struct descrip *)bp);

   /*
    * Set all fields in the new record to null value.
    */
   for (i = bp->nfields; i > nargs; i--)
      rp->fields[i-1] = nulldesc;

   /*
    * Assign each argument value to a record element and dereference it.
    */
   for ( ; i > 0; i--) {
      rp->fields[i-1] = Arg(i);
      DeRef(rp->fields[i-1]);
      }

   ArgType(0) = D_Record;
   Arg(0).vword.bptr = (union block *)rp;
   Return;
   }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.