@@ -450,6 +450,173 @@ register pointer s; /*input stream*/
450450 }
451451 vpop ();
452452 return (result ); }
453+
454+ static pointer readbinaryarray (context * ctx , pointer s , pointer subchr , pointer val )
455+ {
456+ register pointer elm ;
457+ numunion nu ;
458+ int i , ch ;
459+ unsigned long size ;
460+ int rank ;
461+ int dim [ARRAYRANKLIMIT ];
462+ unsigned char * buffer ;
463+ pointer entity ;
464+ pointer ret = NIL ;
465+
466+ for (i = 0 ; i < ARRAYRANKLIMIT ; i ++ ) dim [i ] = 0 ;
467+ ch = nextch (ctx ,s );
468+ if (ch != '(' ) error (E_USER , (pointer )"invalid binary array form [(]" );
469+
470+ rank = 0 ;
471+ size = 1 ;
472+ elm = read1 (ctx ,s ); // read size list
473+ while (elm != NIL ) {
474+ if ( isint (elm -> c .cons .car ) ) {
475+ dim [rank ] = intval (elm -> c .cons .car );
476+ size *= dim [rank ];
477+ rank ++ ;
478+ }
479+ elm = elm -> c .cons .cdr ;
480+ }
481+ elm = read1 (ctx ,s ); // read elemtype
482+
483+ if (elm == K_FLOAT || elm == K_FLOAT32 ) {
484+ entity = makefvector (size );
485+ #ifdef x86_64
486+ buffer = malloc (sizeof (float ) * size );
487+ #else
488+ buffer = (unsigned char * ) & (entity -> c .fvec .fv [0 ]);
489+ #endif
490+ size *= 4 ;
491+ } else if (elm == K_DOUBLE ) {
492+ entity = makefvector (size );
493+ #ifdef x86_64
494+ buffer = (unsigned char * ) & (entity -> c .fvec .fv [0 ]);
495+ #else
496+ buffer = malloc (sizeof (double ) * size );
497+ #endif
498+ size *= 8 ;
499+ } else if (elm == K_SHORT ) {
500+ entity = makeivector (size );
501+ buffer = malloc (sizeof (short ) * size );
502+ size *= 2 ;
503+ } else if (elm == K_INTEGER ) {
504+ entity = makeivector (size );
505+ #ifdef x86_64
506+ buffer = malloc (sizeof (int ) * size );
507+ #else
508+ buffer = (unsigned char * ) & (entity -> c .ivec .iv [0 ]);
509+ #endif
510+ size *= 4 ;
511+ } else if (elm == K_LONG ) {
512+ entity = makeivector (size );
513+ #ifdef x86_64
514+ buffer = (unsigned char * ) & (entity -> c .ivec .iv [0 ]);
515+ #else
516+ buffer = malloc (sizeof (long long ) * size );
517+ #endif
518+ size *= 8 ;
519+ } else {
520+ error (E_USER , (pointer )"invalid binary element type" );
521+ }
522+ vpush (entity );
523+ if (rank == 1 ) {
524+ // just return vector
525+ ret = entity ;
526+ vpop ();
527+ vpush (ret );
528+ } else {
529+ // make array
530+ ret = alloc (vecsize (speval (ARRAY )-> c .cls .vars ), ELM_FIXED ,
531+ intval (speval (ARRAY )-> c .cls .cix ),
532+ vecsize (speval (ARRAY )-> c .cls .vars ));
533+ ret -> c .ary .entity = entity ;
534+ vpop ();
535+ vpush (ret );
536+ ret -> c .ary .fillpointer = NIL ;
537+ ret -> c .ary .rank = makeint (rank );
538+ ret -> c .ary .offset = makeint (0 );
539+ for (i = 0 ; i < ARRAYRANKLIMIT ; i ++ ) ret -> c .ary .dim [i ] = makeint (dim [i ]);
540+ ret -> c .ary .plist = NIL ;
541+ }
542+
543+ ch = nextch (ctx ,s );
544+ if (ch != '"' ) {
545+ error (E_USER , (pointer )"invalid binary array form [\"]" );
546+ }
547+ i = 0 ;
548+ while ((ch = readch (s )) != EOF ) {
549+ buffer [i ++ ] = ch ;
550+ if (i >= size ) break ;
551+ }
552+ if (i != size ) {
553+ error (E_USER , (pointer )"invalid size of string" );
554+ }
555+ if (elm == K_FLOAT || elm == K_FLOAT32 ) {
556+ #ifdef x86_64
557+ float * src = (float * )buffer ;
558+ eusfloat_t * dst = (eusfloat_t * )& (entity -> c .fvec .fv [0 ]);
559+ for (i = 0 ; i < size /4 ; i ++ ) {
560+ * dst ++ = * src ++ ;
561+ }
562+ free (buffer );
563+ #else
564+ // do nothing
565+ #endif
566+ } else if (elm == K_DOUBLE ) {
567+ #ifdef x86_64
568+ // do nothing
569+ #else
570+ double * src = (double * )buffer ;
571+ eusfloat_t * dst = (eusfloat_t * )& (entity -> c .fvec .fv [0 ]);
572+ for (i = 0 ; i < size /8 ; i ++ ) {
573+ * dst ++ = * src ++ ;
574+ }
575+ free (buffer );
576+ #endif
577+ } else if (elm == K_SHORT ) {
578+ short * src = (short * )buffer ;
579+ eusinteger_t * dst = (eusinteger_t * )& (entity -> c .ivec .iv [0 ]);
580+ for (i = 0 ; i < size /2 ; i ++ ) {
581+ * dst ++ = * src ++ ;
582+ }
583+ free (buffer );
584+ } else if (elm == K_INTEGER ) {
585+ #ifdef x86_64
586+ int * src = (int * )buffer ;
587+ eusinteger_t * dst = (eusinteger_t * )& (entity -> c .ivec .iv [0 ]);
588+ for (i = 0 ; i < size /4 ; i ++ ) {
589+ * dst ++ = * src ++ ;
590+ }
591+ free (buffer );
592+ #else
593+ // do nothing
594+ #endif
595+ } else if (elm == K_LONG ) {
596+ #ifdef x86_64
597+ // do nothing
598+ #else
599+ long long * src = (long long * )buffer ;
600+ eusinteger_t * dst = (eusinteger_t * )& (entity -> c .ivec .iv [0 ]);
601+ for (i = 0 ; i < size /8 ; i ++ ) {
602+ * dst ++ = * src ++ ;
603+ }
604+ free (buffer );
605+ #endif
606+ }
607+
608+ ch = readch (s );
609+ if (ch != '"' ) {
610+ error (E_USER , (pointer )"invalid binary array form / end of [\"]" );
611+ }
612+ ch = nextch (ctx ,s );
613+ while (ch != ')' && ch != EOF ) {
614+ ch = nextch (ctx ,s );
615+ }
616+
617+ return vpop ();
618+ }
619+
453620
454621/****************************************************************/
455622/* read dispatch macro expression
@@ -1058,6 +1225,7 @@ register context *ctx;
10581225 sharpmacro ['I' ]= makeint ((eusinteger_t )readivector );
10591226 sharpmacro ['J' ]= makeint ((eusinteger_t )readobject );
10601227 sharpmacro ['V' ]= makeint ((eusinteger_t )readobject );
1228+ sharpmacro ['G' ]= makeint ((eusinteger_t )readbinaryarray );
10611229
10621230 /* make default readtable */
10631231 rdtable = (pointer )makereadtable (ctx );
0 commit comments