Foros del Web » Programación para mayores de 30 ;) » C/C++ »

Lectura de una matriz alojada en un fichero y almacenamiento en memoria compartida

Estas en el tema de Lectura de una matriz alojada en un fichero y almacenamiento en memoria compartida en el foro de C/C++ en Foros del Web. Hola. Estoy haciendo un programa en el cual se pide en un principio que se creen 4 áreas de memoria compartida (3 áreas para almacenar ...
  #1 (permalink)  
Antiguo 17/05/2017, 17:26
 
Fecha de Ingreso: noviembre-2014
Mensajes: 13
Antigüedad: 2 años, 10 meses
Puntos: 0
Lectura de una matriz alojada en un fichero y almacenamiento en memoria compartida

Hola.

Estoy haciendo un programa en el cual se pide en un principio que se creen 4 áreas de memoria compartida (3 áreas para almacenar una matriz en cada una de ellas y una 4 área para el resultado del ejercicio). A continuación, se nos dice que tenemos que leer una matriz A de un fichero A y una matriz B de un otro fichero B y almacenar ambas matrices en dos de las áreas de memoria compartida creadas (los ficheros son pasados como parámetros por la linea de comandos).

Mi problema es que no soy capaz de leer la matriz A y la B con su respectivo almacenamiento. Lo que he logrado es que sea capaz de hacer o la lectura con la matriz A y su almacenamiento, o bien la lectura con la matriz B y su almacenamiento (de aqui que la ultima linea de codigo del main este comentada, si se deja como codigo y no como comentario se produce una violacion del segmento).

Agradeceria cualquier ayuda. Muchas gracias.


PD1: como restriccion del ejercicio, para leer del fichero solo me dejan utilizar system calls como open, write, read... En ningun momento se puede utilizar fscanf, fprintf....

PD2: la matriz (siempre es cuadrada) esta alojada en el fichero con el siguiente formato:


1;2;3
4;5;6
7;8;9





Código C:
Ver original
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <sys/shm.h>
  4. #include <sys/ipc.h>
  5. #include <sys/types.h>
  6. #include <unistd.h>
  7. #include <fcntl.h>
  8. #include <string.h>
  9.  
  10.  
  11. void pintaMensaje(char texto[], int longitud, int salida); //Salida 1: salida estandar / 2 salida error
  12. void creaMemCompartida(int numFilas, int resultados[]);
  13. int indice(int i, int j, int numColumnas);
  14. void inicializaMatriz(int idFichero, int mat[], int numFilas);
  15.  
  16.  
  17. int main(int arg, char *argv[])
  18. {  
  19.  
  20.  
  21.     //Comprobamos si el numero de parametros pasados es correcto
  22.     if(arg!=6)
  23.     {
  24.         char mensaje[]= "ERROR, el programa debe recibir 5 parametros";
  25.         pintaMensaje(mensaje, sizeof(mensaje),2);
  26.         exit(1);
  27.     }
  28.  
  29.  
  30.  
  31.     //Almacenamos los numeros que recibimos como inputs
  32.     int numFilas= strtol(argv[4],NULL,10); //strtol convierte de string a int -> strtol(string,endptr,base)
  33.     int numProcesos= strtol(argv[5],NULL,10);
  34.  
  35.     //Creamos la memoria compartida que utilizaremos
  36.     int resultados[4];
  37.     creaMemCompartida(numFilas,resultados);
  38.  
  39.    
  40.  
  41.  
  42.     //Una vez creada la memoria, hacemos que uno de nuestros punteros apunten a la zona de  memoria
  43.     //recien creada. Para ello invocamos a la funcion shmat, pasandole el id obtenido anteriormente
  44.     //y un par de parametros que en nuestro caso no nos interesan, por tanto basta con ponerlos a 0
  45.     int *matA=NULL;
  46.     int *matB=NULL;
  47.     int *matC=NULL;
  48.     int *sumaTotal=NULL;
  49.     matA= (int *)shmat(resultados[0],0,0);
  50.     matB= (int *)shmat(resultados[1],0,0);
  51.     matC= (int *)shmat(resultados[2],0,0);
  52.     sumaTotal= (int *)shmat(resultados[3],0,0);
  53.     if(matA==NULL || matB==NULL || matC==NULL || sumaTotal==NULL)
  54.     {
  55.         char mensaje[]="ERROR, no se ha conseguido la memoria compartida";
  56.         pintaMensaje(mensaje, sizeof(mensaje),2);
  57.         exit(1);
  58.     }
  59.  
  60.  
  61.  
  62.  
  63.     /*
  64.         Abrimos los files de la matriz A y B que tenemos que leer
  65.     */     
  66.     int ficheroA = open (argv[1], O_RDONLY);
  67.     int ficheroB = open (argv[2], O_RDONLY);
  68.     if(ficheroA<0 || ficheroB<0)
  69.     {
  70.         char mensaje[]="ERROR, no se han podido abrir los ficheros de las matrices A y B";
  71.         pintaMensaje(mensaje, sizeof(mensaje),2);
  72.         exit(1);
  73.     }
  74.  
  75.    
  76.         inicializaMatriz(ficheroA, matA,numFilas);
  77.     //  inicializaMatriz(ficheroB, matB,numFilas);
  78.  
  79. }
  80.  
  81.  
  82.  
  83.  
  84. void inicializaMatriz(int idFichero, int mat[], int numFilas)
  85. {
  86.         int matriz[numFilas][numFilas];
  87.         int i;
  88.         int j;
  89.        
  90.         char buffer[1024];
  91.         char *aux; 
  92.            
  93.         while (read(idFichero, buffer, 1024)!=0)
  94.         {
  95.             aux=strtok(buffer,";");
  96.            
  97.             while(aux!=NULL)
  98.             {
  99.                 matriz[i][j]=atoi(aux);
  100.                 j++;
  101.                 aux=strtok(NULL,";");
  102.             }
  103.             j=0;
  104.             i++;
  105.         }  
  106.  
  107.         for(i=0; i<3; i++)
  108.         {
  109.             for(j=0; j<3; j++)
  110.             {
  111.                 mat[indice(i,j,numFilas)]= matriz[i][j];
  112.                 printf("matriz[%d][%d]=%d\n",i,j, mat[indice(i,j,numFilas)]);
  113.             }
  114.         }
  115.  
  116. }
  117.  
  118.  
  119.  
  120.  
  121.  
  122.  
  123.  
  124.  
  125.  
  126. void pintaMensaje(char texto[], int longitud, int salida)
  127. {
  128.     write(salida, texto, longitud);
  129.     write(salida, "\n", 1); //Imprimimos un salto de linea para una mejora de la interfaz
  130. }
  131.  
  132.  
  133.  
  134. void creaMemCompartida(int numFilas, int resultados[])
  135. {
  136.    
  137.     //Obtenemos claves para las partes de memoria compartida
  138.     //Todos los procesos que quieran compartir la memoria, deben obtener la misma clave, por esto utilizamos la funcion ftok
  139.     //Esta funcion recibe un fichero cualquiera que exista y que sea accesible (todos los procesos deben pasar el mismo fichero) y un entero cualquiera (todos los procesos el mismo entero)
  140.     key_t claveA= ftok("/bin/ls",30);
  141.     key_t claveB= ftok("/bin/ls",31);
  142.     key_t claveC= ftok("/bin/ls",32);
  143.     key_t claveSuma= ftok("/bin/ls",33);
  144.  
  145.     if(claveA==-1 || claveB==-1 || claveC==-1 || claveSuma==-1)
  146.     {
  147.         char mensaje[]= "ERROR, no se ha conseguido la clave para la memoria compartida";
  148.         pintaMensaje(mensaje, sizeof(mensaje),2);
  149.         exit(1);
  150.     }
  151.    
  152.  
  153.  
  154.  
  155.     //Creamos la memoria con la clave recien conseguida. Para ello llamamos a la funcion
  156.     //shmget pasandole la clave, el tamanho de memoria que queremos reservar en bytes y unos flags
  157.     //Los flags son los permisos de lectura/escritura/ejecucion para propietario, grupos y otros
  158.     //y el flag IPC_CREAT para indicar que cree la memoria
  159.     //La funcion devuelve un identificador para la memoria recien creada
  160.     int id_matA= shmget(claveA, sizeof(int)*numFilas*numFilas, IPC_CREAT|0777);
  161.     int id_matB= shmget(claveB, sizeof(int)*numFilas*numFilas, IPC_CREAT|0777);
  162.     int id_matC= shmget(claveC, sizeof(int)*numFilas*numFilas, IPC_CREAT|0777);
  163.     int id_suma= shmget(claveSuma, sizeof(int), IPC_CREAT|0777);   
  164.    
  165.     if (id_matA ==-1 || id_matB ==-1 || id_matC ==-1 || id_suma ==-1)
  166.     {
  167.         char mensaje[]= "ERROR, no se ha conseguido ID para la memoria compartida";
  168.         pintaMensaje(mensaje, sizeof(mensaje),2);
  169.         exit(1);
  170.     }
  171.  
  172.  
  173.     resultados[0]= id_matA;
  174.     resultados[1]= id_matB;
  175.     resultados[2]= id_matC;
  176.     resultados[3]= id_suma;
  177. }
  178.  
  179.  
  180. int indice(int i, int j, int numColumnas)
  181. {
  182.     return j*numColumnas+i;
  183. }

Última edición por Ojimetro; 17/05/2017 a las 17:39



La zona horaria es GMT -6. Ahora son las 13:58.