Main Page   Namespace List   Class Hierarchy   Compound List   File List   Namespace Members   Compound Members   File Members  

file_io.c

Go to the documentation of this file.
00001 
00007 #include <stdlib.h>
00008 #include <ctype.h>
00009 #include <string.h>
00010 #include <math.h>
00011 
00012 #include "ipc.h" 
00013 #include "cmdparam.h"
00014 #include "tilt.h"
00015 #include "ppm_draw.h" 
00016 #ifndef NO_BINARY
00017 #include "binarysave.h"
00018 #endif
00019 #ifndef NO_INPUTS
00020 #include "inputs.h"
00021 #endif
00022 
00023 #include "analyze.h" 
00024 #include "file_io.h" 
00025 #include "globals.h"
00026 #include "kernel.h"
00027 #include "lissom.h"
00028 
00029 
00030 
00031 /******************************************************************************/
00032 /* Defines and typedefs                                                       */
00033 /******************************************************************************/
00034 #define MAX_FILENAME_LENGTH 128
00035 
00036 
00037 /* 28 Feb 96 J.A.B. If any of these are not defined, the corresponding 
00038    data will not be saved when save_image_data() is called.  Note that 
00039    disabling any of them may interfere with the operation of the 
00040    display_od program, so turning them off should only be done as an 
00041    optimization if using another display method. 
00042    */
00043 #define SAVE_ACTIVITIES
00044 #define SAVE_MAP_DATA
00045 #define SAVE_OD_PREFS
00046 #define SAVE_INPUTS
00047 
00048 
00049 
00050 /******************************************************************************/
00051 /* Parameters                                                                 */
00052 /******************************************************************************/
00053 
00054 int    plot_pe=PARENTPE;
00055 
00056 
00057 
00058 /******************************************************************************/
00059 /* Global variables                                                           */
00060 /******************************************************************************/
00061 
00062 int save_histo_files=False;
00063 
00064 OrientationHistogram map_angles;
00065 OrientationHistogram prev_map_angles;
00066 OrientationHistogram weight_angles;
00067 OrientationHistogram ormap_angles;
00068 
00069 
00070 
00071 /******************************************************************************/
00072 /* Command prototypes                                                         */
00073 /******************************************************************************/
00074 
00075 CMD_DECLARE(activity_distribution);
00076 CMD_DECLARE(dump_lat_wts);
00077 CMD_DECLARE(dump_lat_wts_sq);
00078 CMD_DECLARE(load_snapshot);
00079 CMD_DECLARE(or_pref_distribution);
00080 CMD_DECLARE(plot_afferent_weight_map);
00081 CMD_DECLARE(plot_or_key);
00082 CMD_DECLARE(plot_weights);
00083 CMD_DECLARE(plot_activity);
00084 CMD_DECLARE(read_or_pref);
00085 CMD_DECLARE(save_snapshot);
00086 
00087 
00088 
00089 /******************************************************************************/
00090 /* Prototypes for private functions                                           */
00091 /******************************************************************************/
00092 
00093 int  save_orientation_distribution(OrientationHistogram *histo, const char *histotype, int eye);
00094 void read_afferent_wts(Neuron nmap[NMAX][NMAX], FILE *fp, int ui,int uj, int action);
00095 void read_one_eye_wts(FILE *fp, a_weight affwts[WTMAX][WTMAX],
00096                       int lowk, int highk, int lowl, int highl, int action);
00097 int  read_maple(FILE *fp,l_weight *weights,int radius,int ui,int uj,double
00098                 multiplier, int action);  
00099 void weights_IO(int action, FILE *fp);
00100 
00101 
00102 
00103 /******************************************************************************/
00104 /* Initialization hook                                                        */
00105 /******************************************************************************/
00106 
00107 void  file_io_init_hook( void )
00108 {
00109   CMD_DOC(activity_distribution,"init_network",0,"%s [<lowi> [<highi> [<lowj> [<highj>]]]]",
00110           "Determine the total activation for each or_pref bin, and scale them to the\n"
00111           "total overall level of activity.\n\n"
00112           "Creates a file with a histogram of the percentage of activity for each\n"
00113           "orientation preference.  This gives a way to judge the (an)isotropicity\n"
00114           "of the activated areas -- the histogram should be flat for an unoriented\n"
00115           "stimulus, unless there is some bias for a particular angle in the region\n"
00116           "of stimulus presentation.\n\n"
00117 
00118           "The file is suitable for plotting with xmgr (ACE/gr) or just about any other\n"
00119           "graphing program.");
00120   
00121   /* Disabled -- they don't look safe 
00122   CMD_DOC(dump_lat_wts,"init_network",1,"%s <row>",
00123           "Dumps the lateral weights for the given row to a plain ASCII file for\n"
00124           "debugging.");
00125   
00126   CMD_DOC(dump_lat_wts_sq,"init_network",3,"%s <neuron> <side> <step>",
00127           "Dumps lateral weights in a square region of the net to a plain ASCII\n"
00128           "file for debugging.  Starts with (neuron,neuron) and ends with\n"
00129           "(neuron+side, neuron+side), dumping in steps.  The shmem_get function\n"
00130           "overwrites local weights of PE 0, so this can be called only at the\n"
00131           "end of the simulation.  It cannot be used in conjunction with\n"
00132           "weights_IO if the N-1th PE is involved, because that overwrites the\n"
00133           "(N-1)th PE's weights.");
00134   */
00135   
00136   CMD_DOC(load_snapshot,NULL,0,"%s [<iteration_number> [<filename>]]",
00137           "Load a weight file saved at the indicated iteration, in order to test\n"
00138           "it or continue training.  Binary or ASCII files will be expected\n"
00139           "depending on the value of the compilation constant NO_BINARY.  If no\n"
00140           "iteration is specified, `tend' is assumed; if no filename is specified,\n"
00141           "one is constructed as for save_snapshot at that iteration.  After loading\n"
00142           "the iteration counter will be one higher than the iteration at which the\n"
00143           "file was saved.  If the file was saved at tend, then tend is automatically\n"
00144           "increased by an arbitrary amount after loading so that the reloaded network\n"
00145           "can be used.");
00146   
00147   CMD_DOC(or_pref_distribution,"init_network",0, "%s [<lowi> [<highi> [<lowj> [<highj>]]]]",
00148           "Determine the distribution of or_prefs for each angle.\n\n"
00149           "Creates a file with a histogram of the percentage of neurons for each\n"
00150           "orientation preference.  This gives a way to judge the (an)isotropicity\n"
00151           "of the distribution of orientation preferences -- it should be flat for\n"
00152           "the center of a network trained on a uniform distribution of orientations,\n"
00153           "unless there are orientation biases in the architecture (which there usually\n"
00154           "are).\n\n"
00155           
00156           "The file is suitable for plotting with xmgr (ACE/gr) or just about any other\n"
00157           "graphing program.");
00158   
00159   CMD_DOC(plot_activity,"init_network",0,"%s [<filename>]",
00160           "Generate .ppm plots for input and activation at the current iteration,\n"
00161           "with the graphing format determined by many of the parameters starting\n"
00162           "with `ppm_'.\n\n"
00163 
00164           "From left to right, the plots show:\n\n"
00165 
00166           "  * The retinal input to the left eye.\n\n"
00167 
00168           "  * The initial activity in the cortex, before settling due to lateral\n"
00169           "    interactions.\n\n"
00170 
00171           "  * A histogram of the orientation distribution of the initial activity,\n"
00172           "    if ppm_histograms is true and the relevant data is available.\n\n"
00173 
00174           "  * The final activity in the cortex, after settling due to lateral\n"
00175           "    interactions.\n\n"
00176 
00177           "  * A histogram of the orientation distribution of the final activity,\n"
00178           "    if ppm_histograms is true and the relevant data is available.\n\n"
00179 
00180           "  * The retinal input to the right eye(s), if any.\n\n"
00181 
00182           "See the parameters ppm_retina_subplot, ppm_activity_subplot, and others\n"
00183           "for information about modifying or interpreting the plots.\n\n"
00184           
00185           "If the filename is omitted, one is constructed using a standard format.\n"
00186           "If one is given but starts with a period (e.g. \".activ.ppm\"), a complete\n"
00187           "filename is constructed by appending the given suffix to the current value\n"
00188           "of the filebase parameter.");
00189   
00190 #ifndef NO_PPM
00191   CMD_DOC(plot_or_key,NULL,0,"%s [<num_examples> [<key_length> [<vertical> [<filename>]]]]",
00192           "Generate a PPM plot containing an orientation color key.  The first parameter\n"
00193           "specifies how many example bars to use.  The second specifies the total length\n"
00194           "of the key.  If the third is true then the key will be vertical; by default it\n"
00195           "is horizontal.  Finally, the filename may be specified; otherwise it defaults\n"
00196           "to or_key.ppm.  The only PPM parameter that should affect this plot is\n"
00197           "ppm_paper_based_colors.");
00198 
00199 
00200   CMD_DOC(plot_weights,"init_network",0,"%s [<ui> <uj>]*",
00201           "Generate PPM plots of the weights for the given neuron, with the graphing\n"
00202           "format determined by many parameters in ppm_draw.c.  If no coordinates are\n"
00203           "given, plots the neuron closest to the center of the cortex.\n\n"
00204 
00205           "From left to right, the plots show:\n\n"
00206 
00207           "  * The afferent weights to the left eye plotted on the retina.\n\n"
00208 
00209           "  * The lateral excitatory weights plotted on the cortex.\n\n"
00210 
00211           "  * A histogram of the orientation distribution of lateral excitatory\n"
00212           "    weights, if ppm_histograms is true and the relevant data is available.\n\n"
00213 
00214           "  * The lateral inhibitory weights plotted on the cortex.\n\n"
00215 
00216           "  * A histogram of the orientation distribution of lateral inhibitory\n"
00217           "    weights, if ppm_histograms is true and the relevant data is available.\n\n"
00218 
00219           "  * The afferent weights to the right eye(s), if any, plotted on the\n"
00220           "    retina.\n\n"
00221 
00222           "If ppm_outline_weights is true, each window outlines the area in which\n"
00223           "weights are allowed to exist at the current iteration.\n\n"
00224 
00225           "See the parameters ppm_afferent_subplot, ppm_lateral_subplot, and others\n"
00226           "for information about modifying or interpreting the plots.");
00227 
00228 
00229   CMD_DOC(plot_afferent_weight_map,"init_network",0,"%s [<eye> [<filename>]]",
00230           "Generate a PPM plot of the afferent weights to all (or a subset of)\n"
00231           "neurons, with the graphing format determined by many parameters in\n"
00232           "ppm_draw.c.\n\n"
00233 
00234           "See the parameters ppm_neuron_skip_aff, ppm_interior_border, \n"
00235           "ppm_interior_outline, ppm_afferent_subplot, and others for information\n"
00236           "about modifying or interpreting the plots.");
00237 #endif
00238 
00239   CMD_DOC(read_or_pref,"init_network",2,"%s",
00240           "Read orientation map from saved ASCII file instead of computing it.");
00241   
00242   CMD_DOC(save_snapshot,"init_network",0,"%s [<filename>]",
00243           "Save the current state of the network weights.  Binary or ASCII files\n"
00244           "may be used, depending on the value of the compilation constant\n"
00245           "NO_BINARY.  ASCII files are deprecated and are not guaranteed to be\n"
00246           "working properly.  The binary files should be portable between any\n"
00247           "machines that use the IEEE floating-point format.  If saving via a\n"
00248           "hook, you should use the hooklist after_learning since when the file\n"
00249           "is reloaded the iteration counter is set assuming that file was saved\n"
00250           "after the current iteration completed.");
00251 
00252 
00253   PARAM_I(PARAM_INT,   plot_pe,Uninitialized,NPES-1,
00254           "PE which plots data, e.g. for plot_activity.  By default only a single\n"
00255           "PE plots the data, but when debugging on multiple-PE machines, sometimes\n"
00256           "it is helpful to get plots from every PE (if plot_pe == Uninitialized)\n"
00257           "or just a different PE than usual.  This can help e.g. verify that\n"
00258           "each PE has identical copies of global arrays.");
00259 }
00260 
00261 
00262 
00263 /******************************************************************************/
00264 /* Commands (others also in next section)                                     */
00265 /******************************************************************************/
00266 
00267 
00268 cmdstat cmd_save_snapshot( CMD_ARGS )
00269 {  
00270 
00271 #ifdef NO_WEIGHTS
00272   (void)argv; /* ignored */
00273   (void)argc; /* ignored */
00274   ipc_notify(IPC_ONE,IPC_ERROR,"No weights are allocated");  
00275 #else
00276   const char *filename=(argc>0 ? cmds(argv[0]) : NULL);
00277   
00278   save_current(filename);
00279 #endif
00280   
00281   return CMD_NO_ERROR;
00282 }
00283 
00284 
00285 
00286 cmdstat cmd_load_snapshot( CMD_ARGS )
00287 {  
00288 #ifdef NO_WEIGHTS
00289   (void)argv; /* ignored */
00290   ipc_notify(IPC_ONE,IPC_ERROR,"No weights are allocated");
00291 #else
00292   int iter=(argc>0 ? cmdi(argv[0]) : tend);
00293   const char *filename=(argc>1 ? cmds(argv[1]) : NULL);
00294 
00295   load_current(iter,filename);
00296 #endif
00297 
00298   (void)argc; /* ignored */
00299   
00300   return CMD_NO_ERROR;
00301 }
00302 
00303 
00304 
00305 cmdstat cmd_plot_activity( CMD_ARGS )
00306 {  
00307   const char *filename=(argc>0 ? cmds(argv[0]) : NULL);
00308   
00309 #if (NPES>1)
00310   collect_activation_data(plot_pe);
00311 #endif
00312 
00313 #ifdef NO_INPUTS
00314   const double last_angle_drawn = 0;
00315 #else
00316   const double last_angle_drawn = inputs->angle_of_object(0,0);
00317 #endif
00318 
00319   save_presentation_image(filename, last_angle_drawn, input_vectors,
00320                           init_activity, prev_map_activity,
00321                           presentation);
00322   
00323   return CMD_NO_ERROR;
00324 }
00325 
00326 
00327 
00328 cmdstat cmd_plot_or_key( CMD_ARGS )
00329 {
00330 #ifdef NO_PPM
00331   (void)argc; /* Unused */
00332   (void)argv; /* Unused */
00333   ipc_notify(IPC_ONE,IPC_ERROR,"Not compiled with PPM support");
00334   return CMD_MISC_ERROR;
00335 
00336 #else
00337   const int    num_examples  = (argc>0 ? cmdi(argv[0]) : 13);
00338   const int    key_length    = (argc>1 ? cmdi(argv[1]) : 900);
00339   const int    vertical      = (argc>2 ? cmdi(argv[2]) : False);
00340   const char * filename      = (argc>3 ? cmds(argv[3]) : "or_key.ppm");
00341 
00342   int width;
00343 
00344   ppm_bitmap_initialize();
00345   
00346   ppm_height = (int)(vertical ?
00347                      1.2 * key_length : 
00348                      1.2 * key_length/(num_examples-1));
00349 
00350   if (ppm_height > IMG_SIZE_Y) {
00351     ipc_notify(IPC_ALL,IPC_ERROR,"ppm_plot_or_key: Height %d is too large for image of %d; aborting", 
00352                ppm_height, (int)IMG_SIZE_Y);
00353     return CMD_PARAMETER_ERROR;
00354   }
00355   
00356   width = ppm_draw_or_color_key(num_examples, key_length, vertical, ppm_border);
00357   ppm_write_to_file( filename, filename, width, ppm_height, 255);
00358 #endif
00359   
00360   return CMD_NO_ERROR;
00361 }
00362 
00363 
00364 
00365 cmdstat cmd_plot_afferent_weight_map( CMD_ARGS )
00366 {
00367 #ifdef NO_PPM
00368   (void)argc; /* Unused */
00369   (void)argv; /* Unused */
00370   ipc_notify(IPC_ONE,IPC_ERROR,"Not compiled with PPM support");
00371   return CMD_MISC_ERROR;
00372 
00373 #else
00374   const int  eye             = (argc>0 ? cmdi(argv[0]) : Uninitialized);
00375   const bool has_filename    = argc>1;
00376   const char* filename       = (has_filename ? cmds(argv[1]) : NULL);
00377   const int  combine_eyes    = ppm_combine_alternate_eyes && (num_eyes%2==0);
00378 
00379   char name[MAXFILENAMELENGTH]; 
00380     
00381   if (has_filename) {
00382     snprintf(name,MAXFILENAMELENGTH,"%s",filename);
00383     if (plot_pe == Uninitialized) /* Add PE tag to filename when each PE plots */
00384       snprintf(name+strlen(name),MAXFILENAMELENGTH,".pe%02d",MyPE);
00385   }
00386 
00387   if (plot_pe==Uninitialized || MyPE==plot_pe)
00388     if (combine_eyes ) {
00389       for (int e=0; e<num_eyes; e+=2)
00390         if (e==eye || eye==Uninitialized) {
00391           if (!has_filename) {
00392             snprintf(name,MAXFILENAMELENGTH,"%s.%06d.aff_map%d-%d",filebase, iteration, e+1,e);
00393             if (plot_pe == Uninitialized) /* Add PE tag to filename when each PE plots */
00394               snprintf(name+strlen(name),MAXFILENAMELENGTH,".pe%02d",MyPE);
00395             snprintf(name+strlen(name),MAXFILENAMELENGTH,".ppm");
00396           }
00397           ppm_bitmap_initialize();
00398           ppm_draw_afferent_weight_map(name, e, e+1);
00399         }
00400     }
00401     else
00402       for (int e=0; e<num_eyes; e++)
00403         if (e==eye || eye==Uninitialized) {
00404           if (!has_filename) {
00405             snprintf(name,MAXFILENAMELENGTH,"%s.%06d.aff_map%d",filebase, iteration, e);
00406             if (plot_pe == Uninitialized) /* Add PE tag to filename when each PE plots */
00407               snprintf(name+strlen(name),MAXFILENAMELENGTH,".pe%02d",MyPE);
00408             snprintf(name+strlen(name),MAXFILENAMELENGTH,".ppm");
00409           }
00410           ppm_bitmap_initialize();
00411           ppm_draw_afferent_weight_map(name, e);
00412         }
00413 
00414 #endif
00415   
00416   return CMD_NO_ERROR;
00417 }
00418 
00419 
00420 
00421 
00422 
00423 /******************************************************************************/
00424 /* Public routines                                                            */
00425 /******************************************************************************/
00426 
00428 void save_presentation_image(const char* filename,
00429                              double fname_angle,
00430                              double input_v[RNMAX*RNMAX*MAX_NUM_EYES],
00431                              double initial_activity[NMAX][NMAX], 
00432                              double settled_activity[NMAX][NMAX],
00433                              int pres)
00434 {
00435   
00436 #ifdef SAVE_IMAGES_AS_ASCII
00437   (void)filename; /* Unused */
00438   (void)fname_angle; /* Unused */
00439   (void)input_v[RNMAX*RNMAX*MAX_NUM_EYES]; /* Unused */
00440   (void)initial_activity[NMAX][NMAX]; /* Unused */ 
00441   (void)settled_activity[NMAX][NMAX]; /* Unused */
00442   (void)pres; /* Unused */
00443 
00444   save_image_data(); 
00445 
00446 #else
00447 
00448   /* First PE computes and saves entire image as a ppm file; could be improved
00449      by making each PE responsible for part of the image or for an activity 
00450      or input panel, etc., but the speedup is probably minimal since I imagine
00451      the process is IO-bound.
00452      */
00453   /* Parent calculates bitmap */
00454   if (plot_pe==Uninitialized || MyPE==plot_pe) { 
00455     char buf[MAXFILENAMELENGTH]; 
00456     int width,height;
00457     
00458     ppm_bitmap_initialize();
00459     
00460     /* Compute height and scaling factors */
00461     height = ppm_presentation_height();
00462     if (height < 0) return;
00463     
00464     /* Draw the pictures in memory */
00465     width = ppm_draw_presentation(input_v,initial_activity, settled_activity);
00466 
00467     if (!filename) {
00468       /* Construct filename encoding iteration #, angle, presentation */
00469       snprintf(buf,MAXFILENAMELENGTH, "%s.%06d.%03dp%01d", 
00470               filebase, iteration,
00471               (int)floor(RADIANS_TO_DEGREES(CONSTRAIN_ANGLE(fname_angle))+0.5), pres);
00472       
00473       if (plot_pe == Uninitialized) /* Add PE tag to filename when each PE plots */
00474         snprintf(buf+strlen(buf),MAXFILENAMELENGTH,".pe%02d",MyPE);
00475 
00476       snprintf(buf+strlen(buf),MAXFILENAMELENGTH,".ppm");
00477 
00478       filename=buf;
00479     }
00480     else if (*filename=='.' && isalnum(*(filename+1))) {
00481       /* Treat as a suffix for filebase */
00482       snprintf(buf,MAXFILENAMELENGTH,"%s%s",filebase, filename);       
00483       filename=buf;
00484     }
00485     
00486     ppm_write_to_file( filename, filename, width, height, 255);
00487     
00488     /* ipc_notify(IPC_ALL,IPC_VERBOSE,"Statistics: N=%d, RN=%d, uncorrelation=%g, ppm_cortex_scale=%g, ppm_retina_scale=%g, width=%d, height=%d",
00489            (int)N, (int)RN, (double)uncorrelation,(double)ppm_cortex_scale,(double)ppm_retina_scale, (int)width, (int)height);
00490            */
00491   }
00492 #endif
00493   
00494 }
00495 
00496 
00497 
00510 int save_image_data(void)
00511 {
00512 #ifdef SAVE_MAP_DATA
00513   static double cx[NMAX][MAX_NUM_EYES*NMAX]; /* COG to each eye */
00514   static double cy[NMAX][MAX_NUM_EYES*NMAX];
00515 #endif
00516   int i,j,eye; 
00517   char open_flag[5];
00518   char buf[MAXFILENAMELENGTH];
00519   char out_buffer[NMAX*14*4]; /* 13 is max length of %e output */
00520   char *ptr_tobuf;
00521   /* Files with image data */
00522   FILE *activity_file=NULL, *map_file=NULL, *od_file=NULL, *input_file=NULL; 
00523 
00524   if (AMPARENTPE){    /* The parent opens all the files for I/O */
00525     if (iteration==0) strcpy(open_flag,"w");   /* Start simulation with empty file  */
00526     else strcpy(open_flag,"a");
00527   }
00528 
00529 
00530 #ifdef SAVE_ACTIVITIES
00531   if (AMPARENTPE){    /* The parent opens all the files for I/O */
00532     snprintf(buf,MAXFILENAMELENGTH,"%s.act",filebase )                ;
00533     if( (activity_file=fopen(buf,open_flag))==NULL )
00534       ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", buf );
00535   }
00536   else {     /* Send input data to parent for saving in file    */
00537 #if (NPES>1)
00538   collect_activation_data(plot_pe);
00539 #endif
00540   }
00541 #endif
00542 
00543 #ifdef SAVE_MAP_DATA
00544   {
00545     double center_x, center_y;
00546     int k,l,m;
00547   
00548     for (i=0; i<nrows; i++){
00549       const int row = MAPROW(i);
00550 
00551       for(j=0; j< N; j++)      /* Calculate center of gravities of afferents */
00552         {
00553           const int lowk  = MAX(cortex_map[row][j].centerx-rf_radius,0   );
00554           const int highk = MIN(cortex_map[row][j].centerx+rf_radius,RN-1);
00555           const int lowl  = MAX(cortex_map[row][j].centery-rf_radius,0   );
00556           const int highl = MIN(cortex_map[row][j].centery+rf_radius,RN-1);
00557           
00558           for (m=0; m <num_eyes; m++){
00559             
00560             double sum_of_wts = 0.0;
00561             for(center_x=0, center_y=0, k=lowk; k <= highk; k++)
00562               for(l=lowl; l <= highl; l++)
00563                 {  
00564                   center_x   += ((double)k+0.5) * cortex_map[row][j].weights[m][k-lowk][l-lowl];
00565                   center_y   += ((double)l+0.5) * cortex_map[row][j].weights[m][k-lowk][l-lowl];
00566                   sum_of_wts +=  cortex_map[row][j].weights[m][k-lowk][l-lowl];
00567                 }
00568             
00569             /* Weights for each eye don't add up to 1.0 ==> divide by sum*/
00570             if (sum_of_wts != 0) {
00571               center_x = (center_x)/((double)(RN)*sum_of_wts);
00572               center_y = (center_y)/((double)(RN)*sum_of_wts);
00573             }
00574             cx[row][j+ m*N] = center_x; /* Save in local array of COGs */
00575             cy[row][j+ m*N] = center_y;
00576           }
00577         }
00578     }
00579     
00580     if (AMPARENTPE){    /* The parent opens all the files for I/O */
00581       snprintf( buf,MAXFILENAMELENGTH,"%s.map",filebase );
00582       if( (map_file=fopen(buf,open_flag))==NULL )
00583         ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", buf );
00584     }
00585     else     /* Send data to parent for saving the data in file    */
00586       for (i=0; i<nrows; i++){
00587         const int row = MAPROW(i);
00588         ipc_put( &(cx[row][0]), IPC_DOUBLE, num_eyes*N, 0);
00589         ipc_put( &(cy[row][0]), IPC_DOUBLE, num_eyes*N, 0);
00590       }
00591   }
00592 #endif
00593 
00594 #ifdef SAVE_OD_PREFS
00595 #ifndef NO_ANALYZE
00596   od_preferences(od_pref,cortex_map); /* Calculate the od_prefs of each neuron     */
00597 
00598   if (AMPARENTPE){    /* The parent opens all the files for I/O */
00599     snprintf( buf,MAXFILENAMELENGTH,"%s.od",filebase );
00600     if( (od_file=fopen(buf,open_flag))==NULL )
00601       ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", buf );
00602   }
00603   else                 /* Send the od_pref data to parent           */
00604     for (i=0; i<nrows; i++) {
00605       const int row = MAPROW(i);
00606       ipc_put( &(od_pref[row][0]), IPC_DOUBLE, N, 0);
00607     }
00608 
00609 #endif 
00610 #endif 
00611 
00612 #ifdef SAVE_INPUTS
00613   if (AMPARENTPE){    /* The parent opens all the files for I/O */
00614     snprintf( buf,MAXFILENAMELENGTH,"%s.input",filebase );
00615     if( (input_file=fopen(buf,open_flag))==NULL )
00616       ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", buf );
00617   }
00618 #endif
00619 
00620 
00621 
00622   ipc_barrier();                      /* Sync to ensure all data have arrived  */
00623 
00624 
00625 
00626 
00627   if (AMPARENTPE){                 /* Parent saves all data */
00628 
00629 #ifdef SAVE_ACTIVITIES
00630     for (i=0; i<N; i++){            /* Save activity patterns                */
00631 
00632       for (ptr_tobuf=out_buffer,j=0; j<N; j++,ptr_tobuf += strlen(ptr_tobuf))
00633         sprintf(ptr_tobuf,"%e ", init_activity[i][j]);
00634 
00635 #ifdef CRAY      
00636 #pragma _CRI suppress (resp_to_inp) /* Force data to be loaded from memory   */
00637 #endif
00638       
00639       sprintf( ptr_tobuf,"\n" );
00640 
00641       if (i==0) fprintf(activity_file,"%d %d %d\n", iteration, N, strlen(out_buffer));
00642 
00643       fwrite(out_buffer,sizeof(char),strlen(out_buffer),activity_file);
00644     }
00645 
00646 
00647     for (i=0; i<N; i++){       /* The map_activity has been acquired already */
00648 
00649       for (ptr_tobuf=out_buffer,j=0; j<N; j++,ptr_tobuf += strlen(ptr_tobuf))
00650         sprintf( ptr_tobuf,"%e ",prev_map_activity[i][j] );
00651 
00652       sprintf(ptr_tobuf,"\n");
00653 
00654       fwrite(out_buffer,sizeof(char),strlen(out_buffer),activity_file);
00655     }
00656 #endif
00657 
00658 #ifdef SAVE_MAP_DATA
00659     for (i=0; i<N; i++){           /* The center of gravities for each eye   */
00660 
00661       for (ptr_tobuf=out_buffer,j=0; j<N; j++,ptr_tobuf += strlen(ptr_tobuf))
00662 #ifdef CRAY
00663 #pragma _CRI suppress (cx,cy)      /* Force data to be loaded from memory    */
00664 #endif
00665         for (eye=0; eye<num_eyes; eye++)
00666           sprintf(ptr_tobuf,"%e %e ",
00667                   cx[i][j+eye*N], cy[i][j+eye*N] );
00668       
00669       sprintf( ptr_tobuf,"\n" );
00670       
00671       if (i==0) fprintf(map_file,     "%d %d %d\n", iteration, N, strlen(out_buffer));
00672 
00673       fwrite(out_buffer,sizeof(char),strlen(out_buffer),map_file);
00674     }
00675 #endif
00676 
00677 #ifdef SAVE_OD_PREFS
00678     for (i=0; i<N; i++){           /* The OD values for each eye             */
00679 
00680       for (ptr_tobuf=out_buffer,j=0; j<N; j++,ptr_tobuf += strlen(ptr_tobuf))
00681 #ifdef CRAY
00682 #pragma _CRI suppress (od_pref)    /* Force data to be loaded from memory    */
00683 #endif
00684         sprintf( ptr_tobuf,"%e ",od_pref[i][j] );
00685 
00686       sprintf( ptr_tobuf,"\n" );
00687  
00688       if (i==0) fprintf(od_file,      "%d %d %d\n", iteration, N, strlen(out_buffer));
00689 
00690       fprintf( od_file,"%d: ",i ); /* To help when examining file with editor*/
00691 
00692       fwrite(out_buffer,sizeof(char),strlen(out_buffer),od_file);
00693     }
00694 #endif
00695 
00696 #ifdef SAVE_INPUTS
00697     for (i=0; i<RN; i++){          /* The inputs have been acquired already  */
00698 
00699       for (ptr_tobuf=out_buffer,j=0; j<RN; j++,ptr_tobuf += strlen(ptr_tobuf))
00700         for (eye=0; eye<num_eyes; eye++)        
00701           sprintf( ptr_tobuf,"%e ", input_vectors[INP_INDEX(eye,i,j)]);
00702 
00703       sprintf(ptr_tobuf,"\n");
00704 
00705       if (i==0) fprintf(input_file,   "%d %d %d\n", iteration, N, strlen(out_buffer));
00706 
00707       fwrite(out_buffer,sizeof(char),strlen(out_buffer),input_file);
00708     }
00709 #endif
00710 
00711 #ifdef SAVE_MAP_DATA
00712     fclose(map_file);
00713 #endif  
00714 #ifdef SAVE_ACTIVITIES
00715     fclose(activity_file);
00716 #endif  
00717 #ifdef SAVE_OD_PREFS
00718     fclose(od_file);
00719 #endif
00720 #ifdef SAVE_INPUTS
00721     fclose(input_file);
00722 #endif
00723   }
00724   
00725   return(1);
00726 }  
00727 
00728 
00729 
00737 void weights_IO(int action, FILE *fp)
00738 {
00739 #ifdef NO_WEIGHTS
00740   (void)action;
00741   (void)fp;
00742 #else
00743   int i,j,k,row;
00744 
00745   /* All PEs are involved in READ, but the WRITE is only by the parent.     */
00746   if (action == READ)          /* Read from the file, and store to all PEs  */
00747     for (i=NPEs-1; i>=0; i--){   
00748       
00749       if (AMPARENTPE){                 /* Parent PE does the actual file IO  */
00750 
00751         for(row=0; row<nrows; row++) {
00752           const int map_row = ARBITRARY_MAPROW(row,i);
00753           for (j=0; j<N; j++){   /* Read a row at one shot, and then store  */
00754             int anint;       /* dummy variables to guarantee proper type */
00755             double adouble;
00756 
00757             if (fscanf(fp,"%d",&anint)==EOF) ipc_notify(IPC_ALL,IPC_ERROR,"IO - centerx");
00758             else cortex_map[map_row][j].centerx = anint;
00759             
00760             if (fscanf(fp,"%d",&anint)==EOF) ipc_notify(IPC_ALL,IPC_ERROR,"IO - centery");
00761             else cortex_map[map_row][j].centery = anint;
00762   
00763             for(k=0; k<input_dimension; k++) /* Read into local weight array */
00764               if (fscanf(fp,"%le",&adouble)==EOF) ipc_notify(IPC_ALL,IPC_ERROR,"IO - weights");
00765               else wts[row][j].weights[0][0][k] = adouble;
00766 
00767             for(k=0; k< lat_exc_dimension; k++)/*Read into local weight array*/
00768               if (fscanf(fp,"%le",&adouble)==EOF) ipc_notify(IPC_ALL,IPC_ERROR,"IO - lat_exc_wts");
00769               else wts[row][j].lat_exc_wts[k] = adouble;
00770 
00771             for(k=0; k< lat_inh_dimension; k++)/*Read into local weight array*/
00772               if (fscanf(fp,"%le",&adouble)==EOF)
00773                 ipc_notify(IPC_ALL,IPC_ERROR,"IO - lat_inh_wts");
00774               else wts[row][j].lat_inh_wts[k] = adouble;
00775           } 
00776         }
00777       }
00778       ipc_barrier();                /* Sync all PEs after reading the nrows      */
00779 
00780       if ((i>0) && PEISME(i))/* The i-th PE gets the data just read using */
00781         for(row=0; row<nrows; row++) { /*local ptrs of parent's malloced arrays*/
00782           const int map_row = ARBITRARY_MAPROW(row,i);
00783           for (j=0; j<N; j++){  
00784 
00785             ipc_get(&cortex_map[map_row][j].centerx, IPC_INT, 1, 0);
00786             ipc_get(&cortex_map[map_row][j].centery, IPC_INT, 1, 0);
00787             ipc_get(wts[row][j].weights[0][0], IPC_DOUBLE, input_dimension, 0);
00788             ipc_get(wts[row][j].lat_exc_wts, IPC_DOUBLE, lat_exc_dimension, 0);
00789             ipc_get(wts[row][j].lat_inh_wts, IPC_DOUBLE, lat_inh_dimension, 0);
00790           }
00791         }
00792       ipc_barrier();           /* Sync to ensure PEs have fetched data before the
00793                             * next file operation                           */
00794     }
00795 
00796   else if ((action == WRITE) && AMYOUNGESTPE)
00797     /* Only the last PE does the writing, from last row, back to first */
00798     for (i=NPEs-1; i>=0; i--){ 
00799 
00800       if (i < (NPEs-1))      /* Get a row at one shot, and then store. Use */
00801         for(row=0; row<nrows; row++) { /* local ptrs for the weight arrays  */
00802           const int map_row = ARBITRARY_MAPROW(row,i);
00803           for (j=0; j<N; j++){ 
00804             ipc_get(&cortex_map[map_row][j].centerx, IPC_INT, 1, i);
00805             ipc_get(&cortex_map[map_row][j].centery, IPC_INT, 1, i);
00806 
00807             ipc_get(wts[row][j].weights[0][0], IPC_DOUBLE, input_dimension, i);
00808             ipc_get(wts[row][j].lat_exc_wts, IPC_DOUBLE, lat_exc_dimension, i);
00809             ipc_get(wts[row][j].lat_inh_wts, IPC_DOUBLE, lat_inh_dimension, i);
00810 
00811           }
00812         }
00813 
00814       for(row=0; row<nrows; row++)  {
00815         const int map_row = ARBITRARY_MAPROW(row,i);    
00816         for (j=0; j<N; j++){   
00817 
00818           if ( (fprintf(fp, "%d\n", cortex_map[map_row][j].centerx)) == EOF )
00819             ipc_notify(IPC_ALL,IPC_ERROR,"IO - centerx");
00820           if ( (fprintf(fp, "%d\n", cortex_map[map_row][j].centery)) == EOF )
00821             ipc_notify(IPC_ALL,IPC_ERROR,"IO - centery");
00822 
00823           for(k=0; k < input_dimension; k++)      /* Save local weight array */
00824             if ( (fprintf(fp, "%e\n", wts[row][j].weights[0][0][k])) == EOF )
00825               ipc_notify(IPC_ALL,IPC_ERROR,"IO - weights");
00826           
00827           for(k=0; k < lat_exc_dimension; k++) 
00828             if ( (fprintf(fp, "%e\n", wts[row][j].lat_exc_wts[k])) == EOF )
00829               ipc_notify(IPC_ALL,IPC_ERROR,"IO - lat_exc_wts");
00830 
00831           for(k=0; k < lat_inh_dimension; k++)
00832             if ( (fprintf(fp, "%e\n", wts[row][j].lat_inh_wts[k])) == EOF)
00833               ipc_notify(IPC_ALL,IPC_ERROR,"IO - lat_inh_wts");
00834         }
00835       }
00836     }
00837 #endif
00838 }
00839 
00840 
00841 
00842 cmdstat cmd_dump_lat_wts( CMD_ARGS )
00843 {
00844 #ifdef NO_WEIGHTS
00845   (void)argc; /* ignored */
00846   (void)argv; /* ignored */
00847 #else
00848   /* These don't seem like they could possibly match anything real -- J.A.B. */
00849 #if NMAX == 256
00850   char out_buffer[NMAX*NMAX/16*14] ;
00851 #elif NMAX > 64
00852   char out_buffer[NMAX*NMAX/4*14] ;
00853 #else
00854   char out_buffer[NMAX*NMAX*14] ;
00855 #endif
00856 
00857   int j, k,l;
00858   char buf[MAXFILENAMELENGTH], *ptr_tobuf;
00859   FILE *fp; 
00860   const int row = cmdi(argv[0]);
00861 
00862   (void)argc; /* ignored */
00863 
00864   /* Ensure row is w/in range */
00865   if ( (row < 0) || (row >= N)) {
00866     ipc_notify(IPC_ONE,IPC_ERROR,"Row %d is out of range of the cortex", row);
00867     return CMD_PARAMETER_ERROR;
00868   }
00869 
00870   if (ROWISLOCAL(row)) /* The PE with this row dumps the lateral wts */
00871     {
00872       const int lowk  = MAX(row-inh_rad,0);
00873       const int highk = MIN(row+inh_rad,N-1);
00874 
00875       snprintf(buf,MAXFILENAMELENGTH,"%s.%d.%d.in",filebase,row,iteration);
00876       if ((fp=fopen(buf,"w"))==NULL){
00877         ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", buf );
00878         return CMD_FILE_ERROR;
00879       }
00880       
00881       for (j=0; j<N; j++){
00882         const int lowl  = MAX(j-inh_rad,0);
00883         const int highl = MIN(j+inh_rad,N-1);
00884         
00885         for(ptr_tobuf=out_buffer, k=lowk; k<= highk; k++){
00886           const int partial_idx = PARTIAL_LAT_INDEX(row,j,k,inh_rad,inh_array_width);
00887           for(l=lowl; l<=highl; l++){
00888             sprintf(ptr_tobuf,"%e ", cortex_map[row][j].lat_inh_wts[FULL_LAT_INDEX(partial_idx,l)]);
00889             ptr_tobuf += strlen(ptr_tobuf);
00890           }
00891         }
00892         sprintf(ptr_tobuf,"\n");
00893 
00894         if (j==0) 
00895           fprintf(fp,"%d %d %d %d %d\n", row, iteration, N, inh_rad, 
00896                   strlen(out_buffer));
00897         fwrite(out_buffer,sizeof(char),strlen(out_buffer),fp);
00898       }
00899       fclose(fp);
00900     }
00901 #endif
00902   
00903   return CMD_NO_ERROR;
00904 }
00905 
00906 
00907 
00915 cmdstat cmd_dump_lat_wts_sq( CMD_ARGS )
00916 {
00917 #ifdef NO_WEIGHTS
00918   (void)argc; /* ignored */
00919   (void)argv; /* ignored */
00920 #else
00921 /* These don't seem like they could possibly match anything real -- J.A.B. */  
00922 #if NMAX == 256
00923   char out_buffer[NMAX*NMAX/16*14] ;
00924 #elif NMAX > 64
00925   char out_buffer[NMAX*NMAX/4*14] ;
00926 #else
00927   char out_buffer[NMAX*NMAX*14] ;
00928 #endif
00929   int i, j, k, l; 
00930   char buf[MAXFILENAMELENGTH], *ptr_tobuf;
00931   FILE *fp;
00932   
00933   (void)argc; /* ignored */
00934 
00935   if (AMPARENTPE) /* One PE dumps the lateral wts */
00936     {
00937       const int neuron = cmdi(argv[0]);
00938       const int side   = cmdi(argv[1]);
00939       const int step   = cmdi(argv[2]);
00940 
00941       ipc_notify(IPC_ALL,IPC_WARNING,"In dump_lat_wts_sq. Overwrites PE 0 data!");
00942       ipc_notify(IPC_ALL,IPC_STD,"Neuron=%d; side=%d; step=%d",neuron, side, step);
00943 
00944       ABORT_IF_RANGE_OUTSIDE_CORTEX(neuron,neuron,neuron+side,neuron+side);
00945 
00946       snprintf(buf,MAXFILENAMELENGTH,"%s.%d.%d.lat",filebase,neuron,iteration);
00947 
00948       if ((fp=fopen(buf,"w"))==NULL){
00949         ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", buf );
00950         return CMD_FILE_ERROR;
00951       }
00952       for (i=neuron; i < (neuron+side); i+=step){ 
00953         const int lowk  = MAX(i-inh_rad,0  );
00954         const int highk = MIN(i+inh_rad,N-1);
00955         
00956         if (!ROWISLOCAL(i))  /* Get a row at one shot, and then store. Use */
00957           for (j=neuron; j< (neuron+side); j+=step)
00958             ipc_get(wts[LOCALROW(i)][j].lat_inh_wts, IPC_DOUBLE, MAX_INH_DIMENSION, PEFORROW(i));
00959         
00960         for (j=neuron; j< (neuron+side); j+=step){ 
00961           const int lowl  = MAX(j-inh_rad,0  );
00962           const int highl = MIN(j+inh_rad,N-1);
00963 
00964           for(ptr_tobuf=out_buffer, k=lowk; k<= highk; k++){
00965             const int partial_idx = PARTIAL_LAT_INDEX(i,j,k,inh_rad,inh_array_width);
00966             for(l=lowl; l<=highl; l++){
00967               sprintf(ptr_tobuf,"%e ", wts[LOCALROW(i)][j].lat_inh_wts[FULL_LAT_INDEX(partial_idx,l)]);
00968               ptr_tobuf += strlen(ptr_tobuf);
00969             }
00970           }
00971           sprintf(ptr_tobuf,"\n");
00972 
00973           if ((i==neuron) && (j==neuron)) /* At beginning of file */
00974             fprintf(fp,"%d %d %d %d %d %d %d\n", neuron, side, step, iteration, 
00975                     N, inh_rad, strlen(out_buffer));
00976           fwrite(out_buffer,sizeof(char),strlen(out_buffer),fp);
00977         }
00978       }
00979      fclose(fp); 
00980     }
00981 #endif
00982   
00983   return CMD_NO_ERROR;
00984 }
00985 
00986 
00987 
00988 cmdstat  cmd_read_or_pref( CMD_ARGS )
00989 {
00990   /* const int  gaussfit_flag= cmdi(argv[0]); */
00991   const int  or_iteration = cmdi(argv[1]);
00992 
00993   FILE *or_file;
00994   char buf[MAX_FILENAME_LENGTH];
00995   
00996   (void)argc; /* ignored */
00997 
00998   if (AMPARENTPE) {
00999     snprintf(buf,MAXFILENAMELENGTH,"%s.%d.or",filebase,or_iteration);
01000     if ((or_file=fopen(buf,"r"))==NULL){
01001       ipc_notify(IPC_ALL,IPC_ERROR,"Could not open OR file %s", buf);
01002       return -1;
01003     }
01004     
01005     ipc_notify(IPC_ALL,IPC_STD,"Reading from OR file %s",buf);
01006     
01007     read_or(or_file,0,NMAX,or_pref,or_select); 
01008     fclose(or_file);
01009   }
01010   
01011   or_dumped = (iteration==Uninitialized ? 1 : iteration);
01012   return 0;
01013 }
01014 
01015 
01016 
01017 /* arguments: file pointer, area of OR map to be displayed */
01018 void read_or(FILE * or_fp, int or_min, int or_max,
01019              int    or_preferences[EYE_ARRAY_SIZE][NMAX][NMAX],
01020              double or_selectivities[EYE_ARRAY_SIZE][NMAX][NMAX] ) 
01021 {
01022   int i,j,iter,Nangles,length,eye; 
01023   double max_or;
01024   /* double max_or_r, max_or_l; */
01025   int d1,d2;
01026   double lf1;
01027   
01028   if (fscanf(or_fp,"%d %d %d %d\n", &iter, &d2, &Nangles, &length) == EOF) {
01029     ipc_notify(IPC_ALL,IPC_ERROR,"File problem reading orientation map");
01030     return;
01031   }
01032   else N = d2;
01033   
01034   if (N > NMAX) {
01035     ipc_notify(IPC_ALL,IPC_ERROR,"NMAX needs to be increased to handle this file: N (%d) > NMAX (%d)",N,NMAX);
01036     exit(-1);
01037   }
01038 
01039   for (eye=0; eye<=MAX_NUM_EYES; eye++) 
01040     for (i=0; i<N; i++){
01041       fscanf(or_fp, "%d ", &length); /* printf("length=%d\n",length);*/
01042       for (j=0; j<N; j++) {
01043         if (fscanf(or_fp,"%d %lf ",&d1,&lf1)==EOF)
01044           ipc_notify(IPC_ALL,IPC_ERROR,"Missing OR values");
01045         else {
01046           or_preferences[eye][i][j] = d1;
01047           or_selectivities[eye][i][j] = lf1;
01048         }
01049       }
01050       fscanf(or_fp,"\n"); 
01051     }
01052 
01053   if (or_min <0) or_min=0; if (or_max > N) or_max = N;
01054   /* max_or_l = max_or_r = 0.0; */
01055   max_or = 0.0;
01056 
01057   for (i=or_min; i<or_max; i++)  /* Find the maximum only in this range */
01058     for(j=or_min; j<or_max; j++){
01059       /* if (or_selectivities[0][i][j] > max_or_l) max_or_l = or_selectivities[0][i][j]; 
01060       if (or_selectivities[1][i][j] > max_or_r) max_or_r = or_selectivities[1][i][j];  commented out */
01061       if (or_selectivities[MAX_NUM_EYES][i][j] > max_or) max_or = or_selectivities[MAX_NUM_EYES][i][j]; 
01062     }
01063   ipc_notify(IPC_ALL,IPC_VERBOSE,"Maximum orientation selectivity for combined eyes was %f", max_or);
01064 
01065   /*  max_or_l = 1.0/max_or_l; 
01066       max_or_r = 1.0/max_or_r; 
01067       */
01068   max_or = 1.0/max_or; 
01069 
01070   /*
01071   for (i=0; i<N; i++)
01072     for(j=0; j<N; j++){
01073       or_selectivities[0][i][j] *= max_or_l; 
01074       or_selectivities[1][i][j] *= max_or_r;     
01075       or_selectivities[2][i][j] *= max_or; 
01076     }  * commented out */
01077 }
01078 
01079 
01080 
01087 void read_wts(Neuron nmap[NMAX][NMAX],
01088               const char *basefilename,int ui,int uj,
01089               int output_routine, int iter, int action,
01090               int *centerx, int *centery)
01091 {
01092   FILE *excfile, *inhfile, *aff_file;
01093   char bufexc[MAX_FILENAME_LENGTH], bufinh[MAX_FILENAME_LENGTH], bufz[MAX_FILENAME_LENGTH];
01094 
01095 
01096   if (output_routine != MAPLE) {
01097     ipc_notify(IPC_ALL,IPC_ERROR,"Only Maple weight plot files are supported at this time");
01098     return; 
01099   }
01100 
01101   snprintf(bufexc,MAXFILENAMELENGTH,"%s.%d_%d.%d.ex.mp",basefilename,ui,uj,iter) ;
01102   if( (excfile=fopen(bufexc,"r"))==NULL )
01103     ipc_notify(IPC_ALL,IPC_ERROR,"Could not open excitatory weights file %s",bufexc);
01104   else {
01105     /* Use original exc_radius */  
01106     read_maple(excfile,nmap[ui][uj].lat_exc_wts, (exc_array_width-1)/2, ui,uj,1/( gammaexc),action);
01107     fclose(excfile);
01108   }
01109   
01110   snprintf(bufinh,MAXFILENAMELENGTH,"%s.%d_%d.%d.in.mp",basefilename,ui,uj,iter) ;
01111   if( (inhfile=fopen(bufinh,"r"))==NULL )
01112     ipc_notify(IPC_ALL,IPC_ERROR,"Could not open inhibitory weights file %s",bufinh);
01113   else {
01114     read_maple(inhfile,nmap[ui][uj].lat_inh_wts, inh_rad,               ui,uj,1/(-gammainh),action);
01115     fclose(inhfile); 
01116   }
01117   
01118   snprintf(bufz,MAXFILENAMELENGTH,"%s.%d_%d.%d.aff.mp",basefilename,ui,uj,iter)  ;
01119   if( (aff_file=fopen(bufz,"r"))==NULL)
01120     ipc_notify(IPC_ALL,IPC_ERROR,"Could not open afferent weights file %s",bufz);
01121   else {
01122     /* Hard-coded approximation to center point since it is not saved in the file */
01123     /* If this differs from the actual value, many warnings will be printed by the 
01124        read_afferent_wts routine but the data will NOT be corrected.
01125        If the automatically generated number didn't work, the user needs to
01126        compute the number by hand and specify it with centerx and/or centery
01127        */
01128     if (*centerx == Uninitialized)  *centerx = (RN*ui/N);
01129     if (*centery == Uninitialized)  *centery = (RN*uj/N);
01130     
01131     nmap[ui][uj].centerx = *centerx;
01132     nmap[ui][uj].centery = *centery;
01133     
01134     read_afferent_wts(nmap,aff_file,ui,uj,action);
01135     fclose(aff_file);
01136   }
01137 }
01138 
01139 
01140 
01141 int read_maple(FILE *fp,l_weight *weights,int radius,int ui,int uj,double multiplier, int action)
01142 {
01143   const int lowk     = MAX(ui-radius,0  );
01144   const int highk    = MIN(ui+radius,N-1);
01145   const int lowl     = MAX(uj-radius,0  );
01146   const int highl    = MIN(uj+radius,N-1);
01147   const int ar_width = 2*radius+1;
01148 
01149   int k, l;
01150 
01151   /* Skip to matrix definition */
01152   fscanf(fp,"with(linalg);\nwith(plots);\n");
01153   fscanf(fp,"z := matrix( [ \n");
01154   
01155   /* Read data points */
01156   for(k=lowk; k<=highk; k++){
01157     fscanf(fp,"[");
01158 
01159     for(l=lowl; l<=highl; l++) {
01160       double weight;
01161       const int ptsread = fscanf(fp,"%lg,", &weight);
01162 
01163       if (ptsread != 1) {
01164         ipc_notify(IPC_ALL,IPC_ERROR,"when reading Maple file; ptsread:%d  lowk:%d k:%d  lowl:%d l:%d",
01165                   ptsread,lowk,k,lowl,l);
01166         return -1;
01167       }
01168       switch(action) {
01169       case OVERWRITE:
01170         weights[LAT_INDEX(ui,uj,k,l,radius,ar_width)]  = weight * multiplier; break;
01171       case SUBTRACTFROM:
01172         weights[LAT_INDEX(ui,uj,k,l,radius,ar_width)] -= weight * multiplier; break;
01173       default:
01174         ipc_notify(IPC_ALL,IPC_ERROR,"read_maple: Unknown action:%d",action);
01175         return -1;
01176       }
01177       
01178     }
01179     fscanf(fp,"]");
01180     if ( (k < highk) ) fscanf(fp,",\n");
01181   }
01182 
01183   /* fscanf(fp," ] );\n"); */
01184 
01185   return 0;
01186 }
01187 
01188 
01189 
01190 void read_one_eye_wts(FILE *fp, a_weight affwts[WTMAX][WTMAX],
01191                       int lowk, int highk, int lowl, int highl, int action)
01192 {
01193   int k, l;
01194   double weight;
01195   double dummyf;
01196   char dummyc;
01197   
01198   /* Make sure that actions are valid so that we won't have to check later */
01199   switch(action) {
01200   case OVERWRITE:      break;
01201   case SUBTRACTFROM:   break;
01202   default:
01203     ipc_notify(IPC_ALL,IPC_ERROR,"read_afferent_wts: Unknown action:%d",action);
01204     return;
01205   }
01206 
01207   fscanf(fp,"%c := matrix( [ \n",&dummyc);
01208 
01209   /* Discard empty lines before weights */
01210   for(k=0; k< lowk; k++){
01211     fscanf(fp, "[");
01212     for(l=0; l<(RN-1); l++) 
01213       fscanf(fp,"%le,", &dummyf);
01214     fscanf(fp,"%le],\n", &dummyf);
01215     if (dummyf != 0)
01216       ipc_notify(IPC_ALL,IPC_ERROR,"Centerx is not correct -- Weight found before expected:%g",dummyf);
01217   }
01218 
01219   /* Read lines with weights */
01220   for(k=lowk; k<=highk; k++){
01221     fscanf(fp, "[");
01222 
01223     /* Discard empty columns before weights */
01224     for(l=0; l<lowl; l++) 
01225       fscanf(fp,"%le,",&dummyf);
01226     if (dummyf != 0)
01227       ipc_notify(IPC_ALL,IPC_ERROR,"Centery is not correct -- Weight found before expected:%g",dummyf);
01228       
01229     for(l=lowl; l<= highl; l++) {
01230       fscanf(fp,"%le",&weight);
01231       if (l == RN-1)
01232         fscanf(fp,"]");
01233       else
01234         fscanf(fp,",");
01235       switch(action) {
01236       case OVERWRITE:     affwts[k-lowk][l-lowl]  = weight; break;
01237       case SUBTRACTFROM:  affwts[k-lowk][l-lowl] -= weight; break;
01238       }
01239       if (weight == 0)
01240         ipc_notify(IPC_ALL,IPC_WARNING,"inactive weight found in active area");
01241     }
01242 
01243     /* Discard empty columns after weights */    
01244     if (highl<RN-1) {
01245       for(l=highl+1; l<RN-1; l++)
01246         fscanf(fp,"%le,",&dummyf);
01247       fscanf(fp,"%le]",&dummyf);
01248     }
01249 
01250     if ( (k < (RN-1)) ) fscanf(fp,",\n");
01251     else if (k == (RN-1)) fscanf(fp," ] );\n");
01252   }
01253 
01254   /* Discard empty lines after weights */    
01255   for(k=highk+1; k<RN; k++){
01256     fscanf(fp, "[");
01257     for(l=0; l<(RN-1); l++)
01258       fscanf(fp,"%le,",&dummyf);
01259     fscanf(fp,"%le]",&dummyf);
01260     if ( (k < (RN-1)) ) fscanf(fp,",\n");
01261     else if (k == (RN-1)) fscanf(fp," ] );\n");
01262   }
01263   swallow_line(fp);
01264 }
01265 
01266 
01267 
01268 /* Will print warnings if centerx, centery assumptions do not match the file */
01269 void read_afferent_wts(Neuron nmap[NMAX][NMAX],
01270                        FILE *fp, int ui,int uj, int action)
01271 {
01272   const int lowk  = MAX(nmap[ui][uj].centerx - rf_radius,0   );
01273   const int highk = MIN(nmap[ui][uj].centerx + rf_radius,RN-1);
01274   const int lowl  = MAX(nmap[ui][uj].centery - rf_radius,0   );
01275   const int highl = MIN(nmap[ui][uj].centery + rf_radius,RN-1);
01276   int eye;
01277   
01278   /* Read header for maple */
01279   fscanf(fp,"with(linalg);\nwith(plots);\n");
01280 
01281   /* Read left eye then any others */
01282   for (eye=0; eye<num_eyes; eye++)
01283     read_one_eye_wts(fp, nmap[ui][uj].weights[eye], lowk, highk, lowl, highl, action);
01284 }
01285 
01286 
01287 
01288 cmdstat cmd_or_pref_distribution( CMD_ARGS )
01289 {
01290   const int lowi  = (argc>0 ? cmdi(argv[0]) : 0   );
01291   const int highi = (argc>1 ? cmdi(argv[1]) : NMAX);
01292   const int lowj  = (argc>2 ? cmdi(argv[2]) : 0   );
01293   const int highj = (argc>3 ? cmdi(argv[3]) : NMAX);
01294 
01295   int status=0,eye;
01296 
01297   ABORT_IF_RANGE_OUTSIDE_CORTEX(lowi,lowj,highi,highj);
01298     
01299   if (plot_pe == Uninitialized || MyPE==plot_pe) {
01300     for (eye=0; eye<combined_eyes; eye++) {
01301       status = compute_orientation_distribution(lowi, highi, lowj, highj, &map_angles, NULL, eye);
01302       if (!status) save_orientation_distribution(&map_angles, "or_histo", eye);
01303     }
01304   }
01305   
01306   return status;
01307 }
01308 
01309 
01310 
01311 cmdstat cmd_activity_distribution( CMD_ARGS )
01312 {
01313   const int lowi  = (argc>0 ? cmdi(argv[0]) : 0   );
01314   const int highi = (argc>1 ? cmdi(argv[1]) : NMAX);
01315   const int lowj  = (argc>2 ? cmdi(argv[2]) : 0   );
01316   const int highj = (argc>3 ? cmdi(argv[3]) : NMAX);
01317 
01318   int status=0,eye;
01319 
01320   ABORT_IF_RANGE_OUTSIDE_CORTEX(lowi,lowj,highi,highj);
01321   
01322 #if (NPES>1)
01323   collect_activation_data(plot_pe);
01324 #endif
01325   
01326   if (MyPE == plot_pe || plot_pe == Uninitialized) {
01327     /* compute histograms for each activation type */
01328     for (eye=0; eye<combined_eyes; eye++) {
01329       
01330       status = compute_orientation_distribution(lowi, highi, lowj, highj, &map_angles,      init_activity,     eye);
01331       if (status)
01332         return status;
01333       else
01334         save_orientation_distribution(&map_angles, "act_histo.i", eye);
01335       
01336       status = compute_orientation_distribution(lowi, highi, lowj, highj, &prev_map_angles, prev_map_activity, eye);
01337       if (!status) save_orientation_distribution(&map_angles, "act_histo.s", eye);
01338     }
01339   }
01340   
01341   return status;
01342 }
01343 
01344 
01345 
01348 int compute_orientation_distribution(int lowi, int highi, int lowj, int highj, OrientationHistogram *histo, double activity[NMAX][NMAX],int eye)
01349 {
01350   int i,j,angle;
01351   
01352   ABORT_IF_RANGE_OUTSIDE_CORTEX(lowi,lowj,highi,highj);
01353   VERIFY_ORPREF_AVAILABLE(10,compute_orientation_distribution);
01354 
01355   /* Initialize all counts */
01356   histo->total_level=0;
01357   for (angle=0; angle < or_num_angles; angle++) 
01358     histo->levels[angle] = 0; 
01359   
01360   /* Add each neuron's activation to the appropriate bin */
01361   for (i=lowi; i <= highi; i++)
01362     for (j=lowj; j <= highj; j++) {
01363       angle = or_pref[eye][i][j];
01364       if ((angle >= 0) && (angle < or_num_angles)) {
01365         double value = 1.0;
01366         /* Use activity if given, or just count everything as 1.0 */
01367         if (activity != NULL)
01368           value = activity[i][j];
01369         
01370         histo->levels[angle]+= value;
01371         histo->total_level  += value;
01372       }
01373     }
01374 
01375   return NO_ERROR;
01376 }
01377 
01378 
01379 
01382 int compute_weight_distribution(OrientationHistogram *histo,
01383                                 int ui, int uj,
01384                                 l_weight *weights,
01385                                 int radius, int ar_width, int eye)
01386 {
01387   const int lowi     = MAX(ui-radius,0);
01388   const int highi    = MIN(ui+radius,N-1);
01389   const int lowj     = MAX(uj-radius,0);
01390   const int highj    = MIN(uj+radius,N-1);
01391 
01392   int i,j,angle;
01393 
01394   VERIFY_ORPREF_AVAILABLE(9,compute_weight_distribution);
01395 
01396   /* Initialize all counts */
01397   histo->total_level=0;
01398   for (angle=0; angle < or_num_angles; angle++) 
01399     histo->levels[angle] = 0; 
01400   
01401   /* Add each neuron's weight to the appropriate bin */
01402   for (i=lowi; i <= highi; i++)
01403     for (j=lowj; j <= highj; j++) {
01404       angle = or_pref[eye][i][j];
01405       if ((angle >= 0) && (angle < or_num_angles)) {
01406         const double value = weights[(i-ui+radius)*ar_width + (j-uj+radius)];
01407         
01408         histo->levels[angle]+= value;
01409         histo->total_level  += value;
01410       }
01411     }
01412 
01413   return NO_ERROR;
01414 }
01415 
01416 
01417      
01418 int save_orientation_distribution(OrientationHistogram *histo, const char *histotype, int eye )
01419 {
01420   if (histo->total_level == 0)
01421     ipc_notify(IPC_ALL,IPC_ERROR,"No activity was found; cannot create histogram file");
01422   else {
01423     int angle;
01424     /* Save data to a file for graphing */
01425     
01426     char filename[50];
01427     static FILE *act_histo_file;    
01428     
01429     /* Open file */
01430     snprintf(filename,MAXFILENAMELENGTH,"%s.%06d.%s_%d",filebase,iteration,histotype,eye);
01431     if (plot_pe == Uninitialized) /* Add PE tag to filename when each PE plots */
01432       snprintf(filename+strlen(filename),MAXFILENAMELENGTH,".pe%02d",MyPE);
01433     
01434     if( (act_histo_file=fopen(filename,"w"))==NULL ) {
01435       ipc_notify(IPC_ALL,IPC_ERROR,"File %s not opened", filename );
01436       return CMD_FILE_ERROR;
01437     }
01438     
01439     /* Print header */
01440     fprintf(act_histo_file,"# Orientation histogram at iteration %d.\n",iteration);
01441     fprintf(act_histo_file,"# Angle Percentage   Level (out of %5.4f total)\n",histo->total_level);
01442     
01443     /* Print count for each angle */
01444     for (angle=0; angle < or_num_angles; angle++) 
01445       fprintf(act_histo_file,"  %5.1f      %5.1f   %7.4f \n",
01446               1.0*OR_PREF_TO_DEGREES(angle),
01447               (100.0*histo->levels[angle])/histo->total_level,
01448               histo->levels[angle]);
01449     
01450     fclose(act_histo_file);
01451     
01452     ipc_notify(IPC_ONE,IPC_STD,"Created %s", filename);
01453     
01454   }
01455 
01456   return NO_ERROR;
01457 }
01458 
01459 
01460 
01461 cmdstat cmd_plot_weights( CMD_ARGS )
01462 {
01463   int ui=MAX(0,N/2-1);
01464   int uj=MAX(0,N/2-1);
01465   int iarg,jarg;
01466 
01467   cmdstat status = CMD_NO_ERROR;
01468 
01469   if (argc%2 != 0) {
01470     ipc_notify(IPC_ONE,IPC_ERROR,"Wrong number of arguments to plot_weights (%d)",argc);
01471     return CMD_PARAMETER_ERROR;
01472   }
01473 
01474   if (argc==0) {
01475     ipc_notify(IPC_ONE,IPC_STD,"Plotting weights for neuron (%d,%d)",ui,uj);
01476     if (ROWISLOCAL(ui)) /* The wts are local to this processor */
01477       status = plot_weights_to_file(ui, uj, filebase,iteration);
01478   }
01479 
01480   else for (iarg=0,jarg=1; jarg<argc; iarg+=2,jarg+=2) {
01481     ui = cmdi(argv[iarg]);
01482     uj = cmdi(argv[jarg]);
01483     
01484     ABORT_IF_NEURON_OUTSIDE_CORTEX(ui,uj);
01485     
01486     ipc_notify(IPC_ONE,IPC_STD,"Plotting weights for neuron (%d,%d)",ui,uj);
01487     
01488     if (ROWISLOCAL(ui)) /* The wts are local to this processor */
01489       status = plot_weights_to_file(ui, uj, filebase, iteration);
01490   }
01491   
01492   return status;
01493 }
01494 
01495 
01496 
01497 int plot_weights_to_file(int ui, int uj, char *filebasename,int iter)
01498 {
01499 #ifdef NO_PPM
01500   (void)ui;           /* Unused */
01501   (void)uj;           /* Unused */
01502   (void)filebasename; /* Unused */
01503   (void)iter;         /* Unused */
01504   ipc_notify(IPC_ONE,IPC_ERROR,"Not compiled with PPM support");
01505   return CMD_MISC_ERROR;
01506 
01507 #else
01508   int height=0, width=0;
01509   char filename[MAXFILENAMELENGTH];
01510 
01511   ppm_bitmap_initialize();
01512   
01513   height = ppm_presentation_height();
01514   if (height < 0) return CMD_MISC_ERROR;
01515   
01516   /* Draw the pictures in memory */
01517   width = ppm_draw_weights(ui,uj);
01518   
01519   /* Construct filename encoding iteration # */
01520   snprintf(filename,MAXFILENAMELENGTH,"%s.%06d.wts.%03d_%03d.ppm",filebasename,iter,ui,uj);
01521 
01522   /* Write PPM output file */
01523   if (ppm_write_to_file( filename, filename, width, height, 255))
01524     return CMD_FILE_ERROR;
01525 
01526   return CMD_NO_ERROR;
01527 #endif
01528 }
01529 
01530 
01531 
01532 /******************************************************************************/
01533 /* Utility functions                                                          */
01534 /******************************************************************************/
01535 
01536 
01538 void swallow_line(FILE *stream)
01539 {
01540   int c = (int)' ';
01541 #ifdef DEBUG_FILE_READING  
01542   printf("Swallowing:");
01543 #endif 
01544 
01545   while ( (c != EOF) && (c != '\n') ) {
01546     c = fgetc(stream);
01547 #ifdef DEBUG_FILE_READING  
01548     printf("%c",(char)c); 
01549 #endif 
01550   }
01551 }
01552 
01553 
01554 

Generated at Mon Aug 21 00:30:54 2000 for RF-LISSOM by doxygen1.2.1 written by Dimitri van Heesch, © 1997-2000