/**
 * Implementación en C de la práctica, para que tengáis una
 * versión funcional en alto nivel de todas les funciones que tenéis 
 * que implementar en ensamblador.
 * Desde este código se hacen las llamadas a les subrutinas de ensamblador. 
 * ESTE CÓDIGO NO SE PUEDE MODIFICAR Y NO HAY QUE ENTREGARLO.
 * */
 
#include <stdio.h>
#include <termios.h>    //termios, TCSANOW, ECHO, ICANON
#include <unistd.h>     //STDIN_FILENO

/**
 * Constantes
 */
 
#include <stdio.h>
#include <termios.h>    //termios, TCSANOW, ECHO, ICANON
#include <unistd.h>     //STDIN_FILENO

/**
 * Constants.
 **/
#define DIMMATRIX 5

/**
 * Definición de variables globales
 */
extern int developer;//Variable declarada en ensamblador con el nombre del programador

char  charac;      //Carácter leído de teclado y para escribir en pantalla.
int   rowScreen;   //Fila donde queremos posicionar el cursor a la pantalla.
int   colScreen;   //Columna donde queremos posicionar el cursor a la pantalla.

char mSecretPlay[2][DIMMATRIX] = { {' ',' ',' ',' ',' '},   //Fila 0: Combinación secreta.
                                   {' ',' ',' ',' ',' '}};  //Fila 1: Jugada.
   int  col = 0;    //Columna que estamos accediendo de la matriz.

   int  state = 0;  //Estado del juego
                    //-1: Se ha pulsado ESC para salir.
                    // 0: Estamos entrando la combinación secreta.
                    // 1: Estamos entrando la jugada.
                    // 2: La combinación secreta tiene espacios o valores repetidos.
                    // 3: Se ha ganado, jugada = combinación secreta.
                    // 4: Se han agotado los intentos.

   long  tries = 5; //Intentos que quedan.
   short hX;        //Aciertos en el lugar.


/**
 * Definición de las funciones de C
 **/
void clearScreen_C();
void gotoxyP1_C();
void printchP1_C();
void getchP1_C();
void printMenuP1_C();
void printBoardP1_C();

void posCurScreenP1_C();
void updateColP1_C();
void updateMatrixBoardP1_C();
void getSecretPlayP1_C();
void printSecretP1_C();
void checkSecretP1_C();
void printHitsP1_C();
void checkPlayP1_C();
void printMessageP1_C();
void playP1_C();

/**
 * Definición de las subrutinas de ensamblador que se llaman des de C.
 **/
void posCurScreenP1();
void updateColP1();
void updateMatrixBoardP1();
void getSecretPlayP1();
void printSecretP1();
void checkSecretP1();
void printHitsP1();
void checkPlayP1();
void playP1();


/**
 * Borrar la pantalla
 * 
 * Variables globales utilizadas:	
 * Ninguna.
 * 
 * Esta función no es llama desde ensamblador
 * y no hay definida una subrutina de ensamblador equivalente.
 */
void clearScreen_C(){
	
    printf("\x1B[2J");
    
}


/**
 * Situar el cursor en una fila indicada por la variable (rowScreen) y 
 * en la columna indicada por la variable (colScreen) de la pantalla.
 * 
 * Variables globales utilizadas:	
 * (rowScreen): Fila de la pantalla donde posicionamos el cursor.
 * (colScreen): Columna de la pantalla donde posicionamos el cursor.
 * 
 * Se ha definido una subrutina en ensamblador equivalente 'gotoxyP1'  
 * para poder llamar a esta función guardando el estado de los registros 
 * del procesador. Esto se hace porque las funciones de C no mantienen 
 * el estado de los registros.
 */
void gotoxyP1_C(){
	
   printf("\x1B[%d;%dH",rowScreen,colScreen);
   
}


/**
 * Mostrar un carácter guardado en la variable (c) en pantalla,
 * en la posición donde está el cursor.
 * 
 * Variables globales utilizadas:	
 * (charac)   : Carácter que queremos mostrar.
 * 
 * Se ha definido un subrutina en ensamblador equivalente 'printchP1' 
 * para llamar a esta función guardando el estado de los registros del 
 * procesador. Esto se hace porque las funciones de C no mantienen 
 * el estado de los registros.
 */
void printchP1_C(){

   printf("%c",charac);
   
}


/**
 * Leer una tecla y guardar el carácter asociado en la variable (charac)
 * sin mostrarlo en pantalla. 
 * 
 * Variables globales utilizadas:	
 * (charac)   : Carácter que leemos de teclado.
 * 
 * Se ha definido una subrutina en ensamblador equivalente 'getchP1' para
 * llamar a esta función guardando el estado de los registros del procesador.
 * Esto se hace porque las funciones de C no mantienen el estado de los 
 * registros.
 */
void getchP1_C(){

   static struct termios oldt, newt;

   /*tcgetattr obtener los parámetros del terminal
   STDIN_FILENO indica que se escriban los parámetros de la entrada estándar (STDIN) sobre oldt*/
   tcgetattr( STDIN_FILENO, &oldt);
   /*se copian los parámetros*/
   newt = oldt;

   /* ~ICANON para tratar la entrada de teclado carácter a carácter no cómo linea entera acabada con /n
      ~ECHO para que no muestre el carácter leído*/
   newt.c_lflag &= ~(ICANON | ECHO);          

   /*Fijar los nuevos parámetros del terminal para la entrada estándar (STDIN)
   TCSANOW indica a tcsetattr que cambie los parámetros inmediatamente. */
   tcsetattr( STDIN_FILENO, TCSANOW, &newt);

   /*Leer un carácter*/
   charac = (char) getchar();                 
    
   /*restaurar los parámetros originales*/
   tcsetattr( STDIN_FILENO, TCSANOW, &oldt);
   
}


/**
 * Mostrar en pantalla el menú del juego y pedir una opción.
 * Sólo acepta una de las opciones correctas del menú ('0'-'8')
 * 
 * Variables globales utilizadas:		
 * (developer):((char *)&developer): Variable definida en el código ensamblador.
 * (rowScreen): Fila de la pantalla donde posicionamos el cursor.
 * (colScreen): Columna de la pantalla donde posicionamos el cursor.
 * (charac)   : Carácter que leemos de teclado.
 * 
 * 
 * Esta función no se llama desde ensamblador
 * y no hay definida una subrutina de ensamblador equivalente.
 */
 
void printMenuP1_C(){
	
   clearScreen_C();
   rowScreen = 1;
   colScreen = 1;
   gotoxyP1_C();
   printf("                              \n");
   printf("       Developed by:          \n");
   printf("     ( %s )   \n",(char *)&developer);
   printf(" _____________________________ \n");
   printf("|                             |\n");
   printf("|    MENU MASTERMIND v1.0     |\n");
   printf("|_____________________________|\n");
   printf("|                             |\n");
   printf("|     1.  PosCurScreen        |\n");
   printf("|     2.  UpdateCol           |\n");
   printf("|     3.  UpdateMatrixBoard   |\n");
   printf("|     4.  getSecretPlay       |\n");
   printf("|     5.  PrintSecret         |\n");
   printf("|     6.  CheckSecret         |\n");
   printf("|     7.  PrintHits           |\n");
   printf("|     8.  CheckPlay           |\n");
   printf("|     9.  Play Game           |\n");
   printf("|     0.  Play Game C         |\n");
   printf("|    ESC. Exit game           |\n");
   printf("|                             |\n");
   printf("|         OPTION:             |\n");
   printf("|_____________________________|\n"); 

   charac=' ';
   while (charac!=27 && (charac < '0' || charac > '9')) {
     rowScreen = 21;
     colScreen = 19;
     gotoxyP1_C();
     getchP1_C();
   }
	
}


/**
 * Mostrar el tablero de juego en pantalla. Las líneas del tablero.
 * 
 * Variables globales utilizadas:	
 * (rowScreen): Fila de la pantalla donde posicionamos el cursor.
 * (colScreen): Columna de la pantalla donde posicionamos el cursor.
 * (tries)    : Intentos que quedan.
 *  
 * Esta función se llama des de C y desde ensamblador,
 * y no hay definida una subrutina de ensamblador equivalente.
 */
void printBoardP1_C(){
   int i;

   clearScreen_C();
   rowScreen = 1;
   colScreen = 1;
   gotoxyP1_C();
   printf(" _______________________________ \n");//1
   printf("|                               |\n");//2
   printf("|      _ _ _ _ _   Secret Code  |\n");//3
   printf("|_______________________________|\n");//4
   printf("|                 |             |\n");//5
   printf("|       Play      |     Hits    |\n");//6
   printf("|_________________|_____________|\n");//7
   for (i=0;i<tries;i++){                        //8-19
     printf("|   |             |             |\n");
     printf("| %d |  _ _ _ _ _  |  _ _ _ _ _  |\n",i+1);
   }
   printf("|___|_____________|_____________|\n");//20
   printf("|       |                       |\n");//21
   printf("| Tries |                       |\n");//22
   printf("|  ___  |                       |\n");//23
   printf("|_______|_______________________|\n");//24
   printf(" (ENTER) next Try       (ESC)Exit \n");//25
   printf(" (0-9) values    (j)Left (k)Right   ");//26
   
}
   

/**
 * Posicionar el cursor dentro del tablero según la posición del cursor (col), 
 * de los intentos que quedan (tries) y del estado del juego (state).
 * Si estamos entrando la combinación secreta (state==0) nos pondremos 
 * en la fila 3 (rowScreen=3), si estamos entrando la jugada (state=1)
 * la fila se calcula con la formula: (rowScreen=9+(DIMMATRIX-tries)*2).
 * La columna se calcula con la fórmula (colScreen= 8+(col*2)).
 * Para posicionar el cursor en la pantalla se llamar la función gotoxyP1_C.
 * 
 * Variables globales utilizadas:   
 * (rowScreen): Fila de la pantalla donde posicionamos el cursor.
 * (colScreen): Columna de la pantalla donde posicionamos el cursor.
 * (state)    : Estado del juego.
 * (tries)    : Intentos que queden.
 * (col)      : Columna donde está el cursor.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'posCurScreenP1'.
 **/
void posCurScreenP1_C(){
	
   if (state==0) {
      rowScreen = 3;
   } else {
      rowScreen = 9+(DIMMATRIX-tries)*2;
   }
   colScreen = 8+(col*2);
   gotoxyP1_C();
   
}


/**
 * Actualizar la columna (col) donde está el cursor.
 * Si se ha leído (charac=='j') izquierda o (charac=='k') derecha 
 * actualizar la posición del cursor (col +/- 1)
 * controlando que no salga del vector [0..DIMMATRIX-1]. 
 *  
 * Variables globales utilizadas: 	
 * (charac): Carácter leído desde teclado.
 * (col)   : Columna donde está el cursor.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'updateColP1'.
 **/
void updateColP1_C(){
	
   if ((charac=='j') && (col>0)){             
      col--;
   }
   if ((charac =='k') && (col<DIMMATRIX-1)){
      col++;
   }
   
}


/**
 * Guardar el carácter leído ['0'-'9'] (charac) en la matriz
 * (mSecretPlay) en la fila indicada por la variable (state) y
 * la columna indicada por la variable (col).
 * Si (state==0) cambiaremos el carácter leído por un '*' (charac='*') 
 * para que no se vea la combinación secreta que escribimos.
 * Finalmente mostraremos el carácter (charac) en pantalla en la posición
 * donde está el cursor llamando a la función printchP1_C.
 * 
 * Variables globales utilizadas: 	
 * (charac)    : Carácter a mostrar.
 * (mSecrePlay): Matriz donde guardamos la combinación secreta y la jugada.
 * (col)       : Columna donde está el cursor.
 * (state)     : Estado del juego.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'updateArrayP1'.
 **/
void updateMatrixBoardP1_C(){

   mSecretPlay[state][col] = charac;
   if (state==0) {
      charac='*';
   }    
   printchP1_C();
   
}


/**
 * Leer los caracteres de la combinación secreta o la jugada.
 * Mientras no se pulse ENTER(10) o ESC(27) hacer lo siguiente:
 * · Posicionar el cursor en pantalla llamando la función posCurScreenP1_C, 
 *   según el valor de las variables (col, tries y state).
 * · Leer un carácter de teclado llamando la función getchP1_C
 *   que retorna en (charac) el código ASCII del carácter leído.
 *   - Si se ha leído una 'j'(izquierda) o una 'k' (derecha) mover el 
 *     cursor por las 5 posiciones de la combinación actualizando 
 *     el valor de la variable (col) llamando la función updateColP1_C
 *     en función de las variables (col, tries y state).
 *   - Si se ha leido un número ['0'-'9'] lo guardamos en la matriz
 *     (mSecretPlay) y lo mostramos llamando la función updateMatrixBoardP1_C
 *     en función de las variables (charac, mSecretPlay, col y state).
 * Si se ha pulsado ESC(27) poner (state=-1) para indicar que tenemos que salir.
 * Si se pulsa ENTER(10) se aceptará la combinación tal cómo esté.
 * NOTA: Hay que tener en cuenta que si se pulsa ENTER sin haber asignado
 * valores a todas las posiciones de la combinación, habrá posiciones 
 * que serán un espacio (valor utilizado para inicializar la matriz).
 * 
 * Variables globales utilizadas:	
 * (charac)     : Carácter a mostrar.
 * (col)        : Columna donde está el cursor.
 * (mSecretPlay): rdi(rdi): Matriz donde guardamos la combinación secreta y la jugada.
 * (state)      : rsi(esi): Estado del juego.
 * (tries)      : rdx(rdx): Número de intentos que quedan.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'getSecretPlayP1'.
 **/
void getSecretPlayP1_C(){
   
   col = 0;
   
   do {
	 posCurScreenP1_C();
	 getchP1_C();
     if (charac=='j' || charac=='k'){             
       updateColP1_C();
     }
     if (charac>='0' && charac<='9'){   
       updateMatrixBoardP1_C();
     }  
   } while (charac!=10 && charac!=27);  

   if (charac == 27) {
     state = -1;    
   }
   
}


/**
 * Verificar que la combinación secreta no tenga el valor inicial (' '),
 * ni números repetidos.
 * Para cada elemento de la fila [0] de la matriz (mSecretPlay) mirar que 
 * no haya un espacio (' ') y que no esté repetido (de la posición 
 * siguiente a la actual hasta el final). Para indicar que la combinación
 * secreta no es correcta pondremos (secretError=1).
 * Si la combinación secreta no es correcta, poner (state=2) para
 * indicarlo.
 * Si no, la combinación secreta es correcta, poner (state=1) para ir
 * a leer jugadas.
 * 
 * Variables globales utilizadas: 
 * (mSecretPlay): rdi(rdi): Matriz donde guardamos la combinación secreta y la jugada.
 * (state)      : rax(eax): Estado del juego.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'checkSecretP1'. 
 **/
void checkSecretP1_C() {
   int i,j;
   int secretError = 0;
     
   for (i=0;i<DIMMATRIX;i++) {
     if (mSecretPlay[0][i]==' ') {
       secretError=1;
     }
     for (j=i+1;j<DIMMATRIX;j++) {
       if (mSecretPlay[0][i]==mSecretPlay[0][j]) {
		 secretError=1;
	   }
     }
   }
   
   if (secretError==1) state = 2; 
   else state = 1; 

}


/**
 * Mostrar una combinación secreta del juego.
 * Muestra la combinación secreta (fila 0 de la matriz mSecretPlay) 
 * en la parte superior del tablero cuando finaliza el juego.
 * Para mostrar los valores se tiene llamar la función gotoxyP1_C para 
 * posicionar el cursor, en la fila 3 (rowScreen=3) y a partir de la 
 * columna 8 (colScreen=8) y printchP1_C para mostrar cada carácter.
 * Incrementar la columna (colScreen) de 2 en 2. 
 * 
 * Variables globales utilizadas: 	
 * (rowScreen)  : Fila de la pantalla donde posicionamos el cursor.
 * (colScreen)  : Columna de la pantalla donde posicionamos el cursor.
 * (charac)     : Carácter a mostrar.
 * (mSecretPlay): Matriz donde guardamos la combinación secreta y la jugada.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'printSecretP1'.  
 **/
void printSecretP1_C() {
	
   int i;
   rowScreen = 3;
   colScreen = 8;
   
   for (i=0; i<DIMMATRIX; i++){
	 gotoxyP1_C();
	 charac = mSecretPlay[0][i];
     printchP1_C(charac);
     colScreen = colScreen + 2;     
   }
   
}


/**
 * Mostrar los aciertos en su sitio.
 * Situar el cursor en la fila (rowScreen = 9+(DIMMATRIX-tries)*2) y 
 * la columna (colScreen = 22) (parte derecha del tablero) para mostrar 
 * los aciertos en el tablero de juego.
 * Primero se muestran los aciertos en su sitio (hX), tantas 'X' cómo 
 * aciertos en su sitio hayan.
 * Para mostrar los aciertos se tiene que llamar la función gotoxyP1_C para 
 * posicionar el cursor y printchP1_C para mostrar los caracteres. 
 * Cada vez que se muestra un acierto se tiene que incrementar
 * la columna (colScreen) de 2 en 2.
 * NOTA: (hX tiene que ser inferior o igual que DIMMATRIX).
 * 
 * Variables globales utilizadas: 	
 * Ninguna. 
 * 
 * Parámetros de entrada: 
 * (rowScreen): Fila de la pantalla donde posicionamos el cursor.
 * (colScreen): Columna de la pantalla donde posicionamos el cursor.
 * (charac)   : Carácter a mostrar.
 * (tries)    : Intentos que quedan.
 * (hX)       : Aciertos en su sitio.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'printHitsP1'.
 **/ 
void printHitsP1_C() {
   int i;
   
   rowScreen = 9 + (DIMMATRIX-tries)*2;
   colScreen = 22;
   charac = 'X';
   
   for(i=hX;i>0;i--) {
     gotoxyP1_C();
     printchP1_C();
     colScreen = colScreen + 2;
   }
   
}


/**
 * Contar los aciertos en su sitio de la jugada
 * respecto de la combinación secreta.
 * Comparar cada elemento de la combinación secreta con 
 * el elemento que hay en la misma posición de la jugada.
 * Si un elemento de la combinación secreta (mSecretPlay[0][i]) es igual a un 
 * elemento de la misma posición de la jugada (mSecretPlay[1][i]) será un 
 * acierto en su sitio 'X' y se tiene que incrementar los aciertos en su sitio (hX++),
 * Si todas las posiciones de la combinación secreta y de la jugada
 * son iguales (hX=DIMMATRIX) hemos ganado y se tiene que modificar 
 * el estado del juego para indicarlo (state=3),
 * si no, mirar si se han agotado los intentos (tries==1), si se han
 * agotado modificar el estado del juego para indicarlo (state=4).
 * Mostrar los aciertos en el sito y fuera de sitio en el tablero de juego
 * llamando a la función printHitsP1_C.
 * 
 * Variables globales utilizadas: 	
 * (mSecretPlay): Dirección de la matriz donde guardamos la combinación secreta y la jugada.
 * (state)      : Estado del juego.
 * (tries)      : Intentos que quedan.
 * (hX)         : Aciertos en su sitio.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'checkPlayP1'.
 **/
void checkPlayP1_C(){

   int i;
   hX = 0;
   for (i=0;i<DIMMATRIX;i++) {
	 if (mSecretPlay[0][i]==mSecretPlay[1][i]) {
       hX++;
     } 
   }
    
   if (hX == DIMMATRIX ) {
     state = 3;
   } else if (tries==1) {
		 state = 4;
   }
   
   printHitsP1_C();
   
}


/**
 * Mostrar un mensaje en la parte inferior derecha del tablero según el 
 * valor de la variable (state).
 * (state) -1: Se ha pulsado ESC para salir.
 *          0: Estamos entrando la combinación secreta.
 *          1: Estamos entrando la jugada.
 *          2: La combinación secreta tiene espacios o valores repetidos.
 *          3: Se ha ganado, jugada = combinación secreta.
 *          4: Se han agotado los intentos.
 *          
 * Se espera que se pulse una tecla para continuar.
 * Mostrar un mensaje debajo del tablero para indicarlo 
 * y se pulse una tecla lo borra.
 * 
 * Variables globales utilizadas: 	
 * (rowScreen): Fila de la pantalla donde posicionamos el cursor.
 * (colScreen): Columna de la pantalla donde posicionamos el cursor.
 * (state)    : Estado del juego.
 * 
 * Se ha definido un subrutina en ensamblador equivalente 'printMessageP1' 
 * para poder llamar a esta función guardando el estado de los registros 
 * del procesador. Esto se hace porque las funciones de C no mantienen 
 * el estado de los registros.
 **/
void printMessageP1_C(){

   rowScreen = 20;
   colScreen = 11;
   gotoxyP1_C();
   switch(state){
     case -1:
       printf(" EXIT: (ESC) PRESSED ");
     break;
     case 0: 
       printf("Write the Secret Code");
     break;
     case 1:
       printf(" Write a combination ");
     break;
     case 2:
       printf("Secret Code ERROR!!! ");
     break;
     case 3:
       printf("YOU WIN: CODE BROKEN!");
     break;
     case 4:
       printf("GAME OVER: No tries! ");
     break;
   }
   rowScreen = 21;
   colScreen = 11;
   gotoxyP1_C(); 
   printf("  Press any key   ");
   getchP1_C();	  
   gotoxyP1_C();  
   printf("                  ");
   
}


/**
 * Función principal del juego
 * Lee la combinación secreta y verifica que sea correcta.
 * A continuación se lee una jugada, compara la jugada con la
 * combinación secreta para determinar los aciertos en su sitio.
 * Repetir el proceso mientras no se acierta la combinación secreta y 
 * mientras queden intentos. Si se pulsa la tecla 'ESC' durante la lectura
 * de la combinación secreta o de una jugada salir.
 * 
 * Pseudo-código:
 * El jugador dispone de 5 intento (tries=5) par acertar
 * la combinación secreta, el estado inicial del juego es 0 (state=0) y
 * el cursor se pone en la columna 0 (col=0).
 * Mostrar el tablero de juego llamando la función printBoardP1_C.
 * 
 * Mientras (state==0) leer la combinación secreta o (state==1) leer
 * la jugada:
 *   - Mostrar los intentos que quedan (tries) para acertar la combinación 
 *     secreta, situar el cursor en la fila 21, columna 5 llamando la función
 *     gotoxyP1_C y mostrar el carácter asociado al valor de la variable.
 *     (tries) sumando '0' y llamando la función printchP1_C.
 *   - Mostrar un mensaje según el estado del juego (state) llamando 
 *     la función printMessageP1_C.
 *   - Posicionar el cursor en el tablero llamando la función posCurBoardP1_C.
 *   - Leer los caracteres de la combinación secreta o de la jugada 
 *     y actualizar el estado del juego llamando la función getSecretPlayP1_C.
 *   - Si estamos introduciendo la combinación secreta (state==0) verificar
 *     que es correcta llamando la función checkSecretP1_C.
 *     Si no, si estamos introduciendo la jugada (state==1) verificar 
 *     los aciertos de la jugada llamando la función checkPlayP1_C,
 *     decrementar los intentos (tries). Inicializar la jugada que
 *     tenemos guardada en la fila 1 de la matriz mSecretPlay con
 *     espacios (' ') para poder introducir una nueva jugada.
 * 
 * Para acabar, mostrar los intentos que quedan (tries) para 
 * acertar la combinación secreta, situar el cursor en la fila 21, 
 * columna 5 llamando la función gotoxyP1_C y mostrar el carácter asociado 
 * al valor de la variable (tries) sumando '0' y llamando la función 
 * printchP1_C, mostrar la combinación secreta llamando la función 
 * printSecretP1_C y finalmente mostrar un mensaje según el estado del 
 * juego (state) llamando la función printMessageP1_C.
 * Se acaba el juego.
 * 
 * Variables globales utilizadas: 	
 * (col)        : Columna donde está el cursor.
 * (state)      : Estado del juego.
 * (tries)      : Intentos que quedan.
 * (rowScreen)  : Fila de la pantalla donde posicionamos el cursor.
 * (colScreen)  : Columna de la pantalla donde posicionamos el cursor.
 * (charac)     : Carácter a mostrar.
 * (mSecretPlay): Matriz donde guardamos la combinación secreta y la jugada.
 * 
 * Esta función no se llama desde ensamblador.
 * Hay una subrutina de ensamblador equivalente 'playP1'. 
 **/
void playP1_C() {
	
   col=0;
   state = 0;
   tries = 5;
   
   printBoardP1_C();
   
   int i;
     
   while (state == 0 || state == 1) {
	 rowScreen=21;
     colScreen=5;  
	 gotoxyP1_C();
	 charac = (char)tries + '0';
     printchP1_C();
     printMessageP1_C();
     posCurScreenP1_C();
     
	 getSecretPlayP1_C();
	 if (state==0) {
	   checkSecretP1_C();
     } else {
       if (state==1) {
	     checkPlayP1_C();
	     tries --;
	   }
	   for (i=0;i<DIMMATRIX;i++) {
		   mSecretPlay[1][i]=' ';
	   }
	 }
     
   }
   
   rowScreen=21;
   colScreen=5;
   gotoxyP1_C();
   charac=tries + '0';
   printchP1_C();
   printSecretP1_C();
   printMessageP1_C();
   
}


/**
 * Programa Principal
 * 
 * ATENCIÓN: Podéis probar la funcionalidad de las subrutinas que se tienen
 * que desarrollar eliminando los comentarios de la llamada a la función 
 * equivalente implementada en C que hay debajo de cada opción.
 * Para al juego completo hay una opción para la versión en ensamblador y 
 * una opción para el juego en C.
 **/
void main(void){   
   int i;
   int op=' ';      

   while (op!=27) {
     printMenuP1_C();	  //Mostrar menú y retornar opción.
     op = charac;
     switch(op){
       case 27:
         rowScreen=23;
         colScreen=1;
         gotoxyP1_C(); 
         break;
       case '1':	          //Posiciona Cursor en el Tablero.
         state=1;
         tries=5;
         col = 0;		
         printBoardP1_C();
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf("   Press any key  ");   
         //=======================================================
         posCurScreenP1();
         //posCurScreenP1_C();
         //=======================================================
         getchP1_C();
         break;
       case '2':	          //Actualizar la columna del cursor.
         state=1;
         tries=5;
	     col = 4;
         printBoardP1_C();
         rowScreen=21;
         colScreen=11;  
         gotoxyP1_C();
         printf(" Press 'j' or 'k' ");
         posCurScreenP1_C();
         getchP1_C();
         if (charac=='j' || charac=='k') {
         //=======================================================
         updateColP1();
         //updateColP1_C();	    
         //=======================================================
         }
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf("   Press any key  ");
         posCurScreenP1_C();
         getchP1_C();
         break;
       case '3': 	     //Actualizar array y mostrarlo en pantalla.
         state=0;
         tries=5;
         col=2;		  
         printBoardP1_C();
         printSecretP1_C();
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf(" Press (0-9) value ");
         posCurScreenP1_C();
         getchP1_C();
         if (charac>='0' && charac<='9'){       
         //=======================================================
         updateMatrixBoardP1();
         //updateMatrixBoardP1_C();
         //=======================================================
         }
         rowScreen=20;
         colScreen=11;
         gotoxyP1_C();
         printf("   To show Secret  "); 
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf("   Press any key   ");
         getchP1_C();
         printSecretP1_C();
         rowScreen=20;
         colScreen=11;
         gotoxyP1_C();
         printf("                   "); 
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf("   Press any key  ");
         getchP1_C();
         break;
       case '4': 	     //Leer la combinación secreta o la jugada
         state=0;
         tries=5;
         col=0;
         for (i=0;i<DIMMATRIX;i++) {
		   mSecretPlay[state][i]=' ';
	     }
         printBoardP1_C();
         printMessageP1_C();	
         //=======================================================
         getSecretPlayP1();
         //getSecretPlayP1_C();
         //=======================================================
         printSecretP1_C();		
         checkSecretP1_C();
         printMessageP1_C();	
         break;
       case '5': 	     //Mostrar la combinación secreta.
         state=0;
         tries=5;
         col=0;
         printBoardP1_C();
         //=======================================================
         printSecretP1();
         //printSecretP1_C();		
         //=======================================================
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf("   Press any key  ");
         getchP1_C();
         break; 
       case '6': 	     //Verificar la combinación secreta.
         state=0;
         tries=5;
         col=0;	
         printBoardP1_C();
         //=======================================================
         checkSecretP1();
         //checkSecretP1_C();
         //=======================================================
         printSecretP1_C();		
         printMessageP1_C();
         break;
       case '7': 	     //Mostrar aciertos.
         state=1;
         tries=5;
         col=0;
         printBoardP1_C();
         hX = 4;
         //=======================================================
         printHitsP1();
         //printHitsP1_C();
         //=======================================================
         rowScreen=21;
         colScreen=11;
         gotoxyP1_C();
         printf("   Press any key  ");
         getchP1_C();
         break;
       case '8': 	     //Contar aciertos en su sitio.
         state=0;
         tries=5;
         col=0;
         printBoardP1_C();
         char  msecretplay2[2][DIMMATRIX] = {{'1','2','3','4','5'}, //Combinación secreta
                                             {'1','4','3','1','4'}};//Jugada 
         for (i=0;i<DIMMATRIX;i++) {
           mSecretPlay[0][i]=msecretplay2[0][i];
           mSecretPlay[1][i]=msecretplay2[1][i];
         } 
         printSecretP1_C();
         state=1;
         rowScreen = 9+(DIMMATRIX-tries)*2;
         colScreen = 8;
         for (i=0; i<DIMMATRIX; i++){
	       gotoxyP1_C();
	       charac = mSecretPlay[1][i];
           printchP1_C();
           colScreen = colScreen + 2;     
         }
         //=======================================================
         checkPlayP1();
         //checkPlayP1_C();
         //=======================================================
         for (i=0;i<DIMMATRIX;i++) {
           mSecretPlay[0][i]=' ';
           mSecretPlay[1][i]=' ';
         } 
         printMessageP1_C();
         break;
       case '9': 	     //Juego completo en ensamblador.
         i=0;
         for (i=0;i<DIMMATRIX;i++) {
           mSecretPlay[0][i]=' ';
           mSecretPlay[1][i]=' ';
         } 
         //=======================================================
         playP1();
         //=======================================================
         break;
       case '0': 	     //Juego completo en C
         i=0;
         for (i=0;i<DIMMATRIX;i++) {
           mSecretPlay[0][i]=' ';
           mSecretPlay[1][i]=' ';
         } 
         //=======================================================
         playP1_C();
         //=======================================================
         break;
     }
   }

}
 

C Language online compiler

Write, Run & Share C Language code online using OneCompiler's C online compiler for free. It's one of the robust, feature-rich online compilers for C language, running the latest C version which is C18. Getting started with the OneCompiler's C editor is really simple and pretty fast. The editor shows sample boilerplate code when you choose language as 'C' and start coding!

Read inputs from stdin

OneCompiler's C online editor supports stdin and users can give inputs to programs using the STDIN textbox under the I/O tab. Following is a sample C program which takes name as input and print your name with hello.

#include <stdio.h>
int main()
{
    char name[50];
    printf("Enter name:");
    scanf("%s", name);
    printf("Hello %s \n" , name );
    return 0;
    
}

About C

C language is one of the most popular general-purpose programming language developed by Dennis Ritchie at Bell laboratories for UNIX operating system. The initial release of C Language was in the year 1972. Most of the desktop operating systems are written in C Language.

Key features:

  • Structured Programming
  • Popular system programming language
  • UNIX, MySQL and Oracle are completely written in C.
  • Supports variety of platforms
  • Efficient and also handle low-level activities.
  • As fast as assembly language and hence used as system development language.

Syntax help

Loops

1. If-Else:

When ever you want to perform a set of operations based on a condition if-else is used.

if(conditional-expression) {
   // code
} else {
   // code
}

You can also use if-else for nested Ifs and if-else-if ladder when multiple conditions are to be performed on a single variable.

2. Switch:

Switch is an alternative to if-else-if ladder.

switch(conditional-expression) {    
case value1:    
 // code    
 break;  // optional  
case value2:    
 // code    
 break;  // optional  
...    
    
default:     
 // code to be executed when all the above cases are not matched;    
} 

3. For:

For loop is used to iterate a set of statements based on a condition.

for(Initialization; Condition; Increment/decrement){  
  // code  
} 

4. While:

While is also used to iterate a set of statements based on a condition. Usually while is preferred when number of iterations are not known in advance.

while(condition) {  
 // code 
}  

5. Do-While:

Do-while is also used to iterate a set of statements based on a condition. It is mostly used when you need to execute the statements atleast once.

do {
  // code 
} while (condition); 

Arrays

Array is a collection of similar data which is stored in continuous memory addresses. Array values can be fetched using index. Index starts from 0 to size-1.

Syntax

One dimentional Array:

data-type array-name[size];

Two dimensional array:

data-type array-name[size][size];

Functions

Function is a sub-routine which contains set of statements. Usually functions are written when multiple calls are required to same set of statements which increases re-usuability and modularity.

Two types of functions are present in C

  1. Library Functions:

Library functions are the in-built functions which are declared in header files like printf(),scanf(),puts(),gets() etc.,

  1. User defined functions:

User defined functions are the ones which are written by the programmer based on the requirement.

How to declare a Function

return_type function_name(parameters);

How to call a Function

function_name (parameters)

How to define a Function

return_type function_name(parameters) {  
  //code
}