Open64 (mfef90, whirl2f, and IR tools)  TAG: version-openad; SVN changeset: 916
cntigchk.c
Go to the documentation of this file.
00001 /*
00002 
00003   Copyright (C) 2000, 2001, Silicon Graphics, Inc.  All Rights Reserved.
00004 
00005   This program is free software; you can redistribute it and/or modify it
00006   under the terms of version 2.1 of the GNU Lesser General Public License 
00007   as published by the Free Software Foundation.
00008 
00009   This program is distributed in the hope that it would be useful, but
00010   WITHOUT ANY WARRANTY; without even the implied warranty of
00011   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
00012 
00013   Further, this software is distributed without any warranty that it is
00014   free of the rightful claim of any third person regarding infringement 
00015   or the like.  Any license provided herein, whether implied or 
00016   otherwise, applies only to this software file.  Patent licenses, if
00017   any, provided herein do not apply to combinations of this program with 
00018   other software, or any other product whatsoever.  
00019 
00020   You should have received a copy of the GNU Lesser General Public 
00021   License along with this program; if not, write the Free Software 
00022   Foundation, Inc., 59 Temple Place - Suite 330, Boston MA 02111-1307, 
00023   USA.
00024 
00025   Contact information:  Silicon Graphics, Inc., 1600 Amphitheatre Pky,
00026   Mountain View, CA 94043, or:
00027 
00028   http://www.sgi.com
00029 
00030   For further information regarding this notice, see:
00031 
00032   http://oss.sgi.com/projects/GenInfo/NoticeExplan
00033 
00034 */
00035 
00036 
00037 
00038 #pragma ident "@(#) libf/fio/cntigchk.c 92.1    06/18/99 10:21:14"
00039 
00040 #include <liberrno.h>
00041 #include <stdlib.h>
00042 #include <string.h>
00043 #include <cray/nassert.h>
00044 #include <cray/dopevec.h>
00045 #include "fio.h"
00046 
00047 extern int _cntig_chk(DopeVectorType *dv,
00048            void **newar,
00049            int *nocontig,
00050            long *extent,
00051            long *nbytes);
00052 
00053 extern int _unpack_arry(void *dvc, DopeVectorType *dvnc);
00054 
00055 /*
00056  *      _cntig_chk - called by unit and format library code to:
00057  *                   1) check for a contiguous array,
00058  *                   2) calculate the extent of the array (number of elts),
00059  *                   3) calculate the number of bytes of the array,
00060  *                   4) allocate a new array if input array is not
00061  *                      contiguous and move the noncontiguous array to
00062  *                      the contiguous array.
00063  *      Synopsis
00064  *              int _cntig_chk( DopeVectorType *dv,
00065  *                              void **newar,
00066  *                              int *nocontig,
00067  *                              long *extent,
00068  *                              long *nbytes);
00069  *              Where
00070  *                      dv      - pointer to input dope vector
00071  *                      newar   - output pointer to new array
00072  *                      nocontig- address of flag for contiguous array
00073  *                      extent  - address of extent of array
00074  *                      nbytes  - address of array size in bytes
00075  *      Return value
00076  *              zero    - no errors
00077  *              nonzero - error code
00078  */
00079 
00080 int
00081 _cntig_chk(DopeVectorType *dv,
00082            void **newar,
00083            int *nocontig,
00084            long *extent,
00085            long *nbytes)
00086 {
00087         long    *base;                  /* pointer to new area */
00088         char    *cbase;                 /* pointer to new area */
00089         long    extnt = 1;              /* extent of input array */
00090         int     i;
00091         long    k;
00092         int     type;
00093         long    nbyts;                  /* element size in bytes */
00094         int     notcontig = 0;          /* contiguous flag */
00095         int     nd;
00096         long    extente;
00097         long    elsize;                 /* element size */
00098         long    id2, id3,id4;
00099         long    id5, id6, id7;
00100         int     badjust;
00101         long    *addr;                  /* for word-oriented data */
00102         char    *baddr;                 /* for byte-oriented data */
00103         void    *addr2, *addr3, *addr4;
00104         void    *addr5, *addr6;
00105 
00106         type = dv->type_lens.type;
00107         nd = dv->n_dim;
00108 
00109         /* set element byte length and stride length */
00110         if (dv->type_lens.type == DVTYPE_ASCII) {
00111                 nbyts = _fcdlen (dv->base_addr.charptr);
00112                 elsize = nbyts;
00113         }
00114         else {
00115                 nbyts = dv->type_lens.int_len >> 3;
00116                 elsize = nbyts >> 3;
00117         }
00118 
00119         /*
00120          * check for contiguous array
00121          */
00122         for (i=0; i < nd; i++) {
00123                 long st;
00124                 long ex;
00125                 extnt *= dv->dimension[i].extent;
00126                 st = dv->dimension[i].stride_mult;
00127                 ex = dv->dimension[i].extent;
00128                 /* ensure all but last dim are contiguous */
00129                 if ((i < nd-1) && ((st * ex) !=
00130                     dv->dimension[i+1].stride_mult))
00131                         notcontig = 1;
00132                 /* ensure last dim is contiguous */
00133                 else if ((i == nd-1) && (st != elsize))
00134                         notcontig = 1;
00135         }
00136 
00137         *nocontig = notcontig;
00138         *extent = extnt;
00139 
00140         /* calculate size of array in bytes */
00141         nbyts *= extnt;
00142         *nbytes = nbyts;
00143 
00144         if (notcontig == 0) {
00145                 *newar = NULL;
00146                 return(0);
00147         }
00148 
00149         /* clear base address */
00150         base = (void *) NULL;
00151         *newar = base;
00152 
00153         /* Allocate size in bytes if not zero.  Zero size is
00154          * legal and should not cause an error.
00155          */
00156         if (nbyts != 0) {
00157                 base = (void *) malloc (nbyts);
00158 
00159                 /* if no memory assigned, error */
00160                 if (base == NULL) {
00161                         return(FENOMEMY);
00162                 /* set fields for null array as well */
00163                 }
00164         }
00165         *newar = base;
00166 
00167         /* if extent is zero, return */
00168         if (nbyts == 0)
00169                 return(0);
00170 
00171         /* Move noncontiguous array to contiguous array. */
00172         badjust = 0;
00173         extente = dv->dimension[0].extent;
00174         if (type == DVTYPE_ASCII) {
00175                 char    *ba;
00176                 cbase = (char *) base;
00177                 baddr = _fcdtocp(dv->base_addr.charptr) +
00178                         badjust * (dv->type_lens.int_len >> 3);
00179 
00180                 switch(nd) {
00181                 case 7:
00182                         for (id7=0; id7<dv->dimension[6].extent; id7++) {
00183                                 addr6 = baddr;
00184                 case 6:
00185                          for (id6=0; id6<dv->dimension[5].extent; id6++) {
00186                                 addr5 = baddr;
00187                 case 5:
00188                           for (id5=0; id5<dv->dimension[4].extent; id5++) {
00189                                 addr4 = baddr;
00190                 case 4:
00191                            for (id4=0; id4<dv->dimension[3].extent; id4++) {
00192                                 addr3 = baddr;
00193                 case 3:
00194                             for (id3=0; id3<dv->dimension[2].extent; id3++) {
00195                                 addr2 = baddr;
00196                 case 2:
00197                              for (id2=0; id2<dv->dimension[1].extent; id2++) {
00198                 case 1:
00199                                 ba = baddr;
00200                                 for (i=0; i<extente; i++) {
00201                                         (void *) memcpy (cbase,ba,elsize);
00202                                         cbase += elsize;
00203                                         ba += dv->dimension[0].stride_mult;
00204                                 }
00205                                 if (nd == 1) goto done;
00206                                 baddr += dv->dimension[1].stride_mult;
00207                              }
00208                             if (nd == 2) goto done;
00209                             baddr  = addr2;
00210                             baddr += dv->dimension[2].stride_mult;
00211                             }
00212                            if (nd == 3) goto done;
00213                            baddr  = addr3;
00214                            baddr += dv->dimension[3].stride_mult;
00215                            }
00216                           if (nd == 4) goto done;
00217                           baddr  = addr4;
00218                           baddr += dv->dimension[4].stride_mult;
00219                           }
00220                          if (nd == 5) goto done;
00221                          baddr  = addr5;
00222                          baddr += dv->dimension[5].stride_mult;
00223                          }
00224                         if (nd == 6) goto done;
00225                         baddr  = addr6;
00226                         baddr += dv->dimension[6].stride_mult;
00227                         }
00228                 }
00229         }
00230         else {                          /* word-oriented data */
00231                 long    *ba;
00232                 k       = 0;
00233                 addr = (long*)dv->base_addr.a.ptr + badjust;
00234 
00235                 switch(nd) {
00236                 case 7:
00237                         for (id7=0; id7<dv->dimension[6].extent; id7++) {
00238                                 addr6 = addr;
00239                 case 6:
00240                          for (id6=0; id6<dv->dimension[5].extent; id6++) {
00241                                 addr5 = addr;
00242                 case 5:
00243                           for (id5=0; id5<dv->dimension[4].extent; id5++) {
00244                                 addr4 = addr;
00245                 case 4:
00246                            for (id4=0; id4<dv->dimension[3].extent; id4++) {
00247                                 addr3 = addr;
00248                 case 3:
00249                             for (id3=0; id3<dv->dimension[2].extent; id3++) {
00250                                 addr2 = addr;
00251                 case 2:
00252                              for (id2=0; id2<dv->dimension[1].extent; id2++) {
00253                 case 1:
00254                                 ba = addr;
00255                                 for (i=0; i<extente; i++) {
00256                                 /* noncharacter single word entities assumed */
00257                                         base[k] = ba[0];
00258                                         k++;
00259                                         ba += dv->dimension[0].stride_mult;
00260                                 }
00261                                 if (nd == 1) goto done;
00262                                 addr += dv->dimension[1].stride_mult;
00263                              }
00264                             if (nd == 2) goto done;
00265                             addr  = addr2;
00266                             addr += dv->dimension[2].stride_mult;
00267                             }
00268                            if (nd == 3) goto done;
00269                            addr  = addr3;
00270                            addr += dv->dimension[3].stride_mult;
00271                            }
00272                           if (nd == 4) goto done;
00273                           addr  = addr4;
00274                           addr += dv->dimension[4].stride_mult;
00275                           }
00276                          if (nd == 5) goto done;
00277                          addr  = addr5;
00278                          addr += dv->dimension[5].stride_mult;
00279                          }
00280                         if (nd == 6) goto done;
00281                         addr  = addr6;
00282                         addr += dv->dimension[6].stride_mult;
00283                         }
00284                 }
00285         }
00286 done:   return(0);
00287 }
00288 /*
00289  *      _unpack_arry  - called by library routines to move a contiguous
00290  *                      array to a noncontiguous array.
00291  *      Synopsis
00292  *              int _unpak_arry(DopeVectorType *dvc,
00293  *                              DopeVectorType *dvnc);
00294  *              Where
00295  *                      dvc     - pointer to the noncontiguous dope vector.
00296  *                      dvnc    - Pointer to the contiguous dope vector.
00297  */
00298 int
00299 _unpack_arry(void *dvc, DopeVectorType *dvnc)
00300 {
00301         long    * restrict base;        /* pointer to new area */
00302         char    * restrict cbase;       /* pointer to new area */
00303         long    extnt = 1;              /* extent of noncontig array */
00304         int     i;
00305         long    k;
00306         int     type;
00307         long    elsize;                 /* element size of data type */
00308         int     nd;
00309         long    extente;
00310         long    id2, id3,id4;
00311         long    id5, id6, id7;
00312         int     badjust;
00313         long    *addr;                  /* for word-oriented data */
00314         char    *baddr;                 /* for byte-oriented data */
00315         void    *addr2, *addr3, *addr4;
00316         void    *addr5, *addr6;
00317 
00318         type = dvnc->type_lens.type;
00319         nd = dvnc->n_dim;
00320 
00321         /* set bytalign flag, element byte length, and stride length */
00322         if (dvnc->type_lens.type == DVTYPE_ASCII)
00323                 elsize = _fcdlen (dvnc->base_addr.charptr);
00324         else
00325                 elsize = dvnc->type_lens.int_len >> 6;
00326 
00327         /* determine extent of array */
00328         for (i=0; i < nd; i++)
00329                 extnt *= dvnc->dimension[i].extent;
00330 
00331         /* Move noncontiguous array to contiguous array. */
00332         extente = dvnc->dimension[0].extent;
00333         base = dvc;
00334         cbase = (char *) base;
00335         badjust = 0;
00336         if (type == DVTYPE_ASCII) {
00337                 char *ba;
00338                 baddr = _fcdtocp(dvnc->base_addr.charptr) +
00339                         badjust * (dvnc->type_lens.int_len >> 3);
00340 
00341                 switch(nd) {
00342                 case 7:
00343                         for (id7=0; id7<dvnc->dimension[6].extent; id7++) {
00344                                 addr6 = baddr;
00345                 case 6:
00346                          for (id6=0; id6<dvnc->dimension[5].extent; id6++) {
00347                                 addr5 = baddr;
00348                 case 5:
00349                           for (id5=0; id5<dvnc->dimension[4].extent; id5++) {
00350                                 addr4 = baddr;
00351                 case 4:
00352                            for (id4=0; id4<dvnc->dimension[3].extent; id4++) {
00353                                 addr3 = baddr;
00354                 case 3:
00355                             for (id3=0; id3<dvnc->dimension[2].extent; id3++) {
00356                                 addr2 = baddr;
00357                 case 2:
00358                              for (id2=0; id2<dvnc->dimension[1].extent; id2++) {
00359                 case 1:
00360                                 ba = baddr;
00361                                 for (i=0; i<extente; i++) {
00362                                         (void *) memcpy (ba,cbase,elsize);
00363                                         cbase += elsize;
00364                                         ba += dvnc->dimension[0].stride_mult;
00365                                         }
00366                                 if (nd == 1) goto done;
00367                                 baddr += dvnc->dimension[1].stride_mult;
00368                              }
00369                             if (nd == 2) goto done;
00370                             baddr  = addr2;
00371                             baddr += dvnc->dimension[2].stride_mult;
00372                             }
00373                            if (nd == 3) goto done;
00374                            baddr  = addr3;
00375                            baddr += dvnc->dimension[3].stride_mult;
00376                            }
00377                           if (nd == 4) goto done;
00378                           baddr  = addr4;
00379                           baddr += dvnc->dimension[4].stride_mult;
00380                           }
00381                          if (nd == 5) goto done;
00382                          baddr  = addr5;
00383                          baddr += dvnc->dimension[5].stride_mult;
00384                          }
00385                         if (nd == 6) goto done;
00386                         baddr  = addr6;
00387                         baddr += dvnc->dimension[6].stride_mult;
00388                         }
00389                 }
00390         }
00391         else {                          /* word-oriented data */
00392                 long *ba;
00393                 k       = 0;
00394                 addr = (long*)dvnc->base_addr.a.ptr + badjust;
00395 
00396                 switch(nd) {
00397                 case 7:
00398                         for (id7=0; id7<dvnc->dimension[6].extent; id7++) {
00399                                 addr6 = addr;
00400                 case 6:
00401                          for (id6=0; id6<dvnc->dimension[5].extent; id6++) {
00402                                 addr5 = addr;
00403                 case 5:
00404                           for (id5=0; id5<dvnc->dimension[4].extent; id5++) {
00405                                 addr4 = addr;
00406                 case 4:
00407                            for (id4=0; id4<dvnc->dimension[3].extent; id4++) {
00408                                 addr3 = addr;
00409                 case 3:
00410                             for (id3=0; id3<dvnc->dimension[2].extent; id3++) {
00411                                 addr2 = addr;
00412                 case 2:
00413                              for (id2=0; id2<dvnc->dimension[1].extent; id2++) {
00414                 case 1:
00415                                 ba = addr;
00416                                 for (i=0; i<extente; i++) {
00417                                         ba[0] = base[k];
00418                                         k++;
00419                                         ba += dvnc->dimension[0].stride_mult;
00420                                 }
00421                                 if (nd == 1) goto done;
00422                                 addr += dvnc->dimension[1].stride_mult;
00423                              }
00424                             if (nd == 2) goto done;
00425                             addr  = addr2;
00426                             addr += dvnc->dimension[2].stride_mult;
00427                             }
00428                            if (nd == 3) goto done;
00429                            addr  = addr3;
00430                            addr += dvnc->dimension[3].stride_mult;
00431                            }
00432                           if (nd == 4) goto done;
00433                           addr  = addr4;
00434                           addr += dvnc->dimension[4].stride_mult;
00435                           }
00436                          if (nd == 5) goto done;
00437                          addr  = addr5;
00438                          addr += dvnc->dimension[5].stride_mult;
00439                          }
00440                         if (nd == 6) goto done;
00441                         addr  = addr6;
00442                         addr += dvnc->dimension[6].stride_mult;
00443                         }
00444                 }
00445         }
00446 done:   return(0);
00447 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines