File:  [local] / rpl / src / sql.c
Revision 1.70: download - view: text, annotated - select for diffs - revision graph
Fri Jan 10 11:15:52 2020 UTC (4 years, 2 months ago) by bertrand
Branches: MAIN
CVS tags: rpl-4_1_32, HEAD
Modification du copyright.

    1: /*
    2: ================================================================================
    3:   RPL/2 (R) version 4.1.32
    4:   Copyright (C) 1989-2020 Dr. BERTRAND Joël
    5: 
    6:   This file is part of RPL/2.
    7: 
    8:   RPL/2 is free software; you can redistribute it and/or modify it
    9:   under the terms of the CeCILL V2 License as published by the french
   10:   CEA, CNRS and INRIA.
   11:  
   12:   RPL/2 is distributed in the hope that it will be useful, but WITHOUT
   13:   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   14:   FITNESS FOR A PARTICULAR PURPOSE.  See the CeCILL V2 License
   15:   for more details.
   16:  
   17:   You should have received a copy of the CeCILL License
   18:   along with RPL/2. If not, write to info@cecill.info.
   19: ================================================================================
   20: */
   21: 
   22: 
   23: #include "rpl-conv.h"
   24: 
   25: 
   26: /*
   27: ================================================================================
   28:   Fonction de récupération des paramètres de connexion à une base SQL
   29: ================================================================================
   30:   Entrées : objet de type liste
   31: --------------------------------------------------------------------------------
   32:   Sorties : pointeur sur un struct_connecteur_swl
   33: --------------------------------------------------------------------------------
   34:   Effets de bord : néant
   35: ================================================================================
   36: */
   37: 
   38: struct_objet *
   39: parametres_sql(struct_processus *s_etat_processus, struct_objet *s_parametres)
   40: {
   41:     struct_liste_chainee            *l_element_courant;
   42: 
   43:     struct_objet                    *s_connecteur;
   44: 
   45:     unsigned char                   *locale;
   46:     unsigned char                   *type_base;
   47:     unsigned char                   *serveur;
   48: #   if defined(MYSQL_SUPPORT) || defined(POSTGRESQL_SUPPORT)
   49:     unsigned char                   *base;
   50:     unsigned char                   *utilisateur;
   51:     unsigned char                   *mot_de_passe;
   52: #   ifdef POSTGRESQL_SUPPORT
   53:     unsigned char                   *sport;
   54: #   endif
   55: 
   56:     unsigned int                    port;
   57: #   endif
   58: 
   59:     if ((*s_parametres).type != LST)
   60:     {
   61:         (*s_etat_processus).erreur_execution = d_ex_erreur_type_argument;
   62:         return(NULL);
   63:     }
   64: 
   65:     l_element_courant = (struct_liste_chainee *) (*s_parametres).objet;
   66: 
   67:     if (l_element_courant == NULL)
   68:     {
   69:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
   70:         return(NULL);
   71:     }
   72: 
   73:     if ((*(*l_element_courant).donnee).type != CHN)
   74:     {
   75:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
   76:         return(NULL);
   77:     }
   78: 
   79:     if ((type_base = conversion_majuscule(s_etat_processus, (unsigned char *)
   80:             (*(*l_element_courant).donnee).objet)) == NULL)
   81:     {
   82:         (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
   83:         return(NULL);
   84:     }
   85: 
   86:     locale = index(type_base, ':');
   87: 
   88:     if (locale != NULL)
   89:     {
   90:         (*locale) = d_code_fin_chaine;
   91:         locale++;
   92:     }
   93: 
   94:     /*
   95:      * Vérifications des types de base de données
   96:      */
   97: 
   98:     if ((strcmp(type_base, "MYSQL") != 0) &&
   99:             (strcmp(type_base, "POSTGRESQL") != 0) &&
  100:             (strcmp(type_base, "SQLITE") != 0))
  101:     {
  102:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  103:         return(NULL);
  104:     }
  105: 
  106:     if ((s_connecteur = allocation(s_etat_processus, SQL)) == NULL)
  107:     {
  108:         (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
  109:         return(NULL);
  110:     }
  111: 
  112:     (*((struct_connecteur_sql *) (*s_connecteur).objet)).type = type_base;
  113: 
  114:     if (locale != NULL)
  115:     {
  116:         if (((*((struct_connecteur_sql *) (*s_connecteur).objet)).locale
  117:                 = malloc((strlen(locale) + 1) * sizeof(unsigned char))) == NULL)
  118:         {
  119:             (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
  120:             return(NULL);
  121:         }
  122: 
  123:         strcpy((*((struct_connecteur_sql *) (*s_connecteur).objet)).locale,
  124:                 locale);
  125: 
  126:         if (((*((struct_connecteur_sql *) (*s_connecteur).objet)).type
  127:                 = realloc((*((struct_connecteur_sql *) (*s_connecteur).objet))
  128:                 .type, (strlen((*((struct_connecteur_sql *) (*s_connecteur)
  129:                 .objet)).type) + 1) * sizeof(unsigned char))) == NULL)
  130:         {
  131:             (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
  132:             return(NULL);
  133:         }
  134:     }
  135:     else
  136:     {
  137:         (*((struct_connecteur_sql *) (*s_connecteur).objet)).locale = NULL;
  138:     }
  139: 
  140:     (*((struct_connecteur_sql *) (*s_connecteur).objet)).pid = getpid();
  141:     (*((struct_connecteur_sql *) (*s_connecteur).objet)).tid = pthread_self();
  142: 
  143:     // Recherche du nom ou de l'adresse du serveur
  144: 
  145:     l_element_courant = (*l_element_courant).suivant;
  146: 
  147:     if (l_element_courant == NULL)
  148:     {
  149:         liberation(s_etat_processus, s_connecteur);
  150:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  151:         return(NULL);
  152:     }
  153: 
  154:     if ((*(*l_element_courant).donnee).type != CHN)
  155:     {
  156:         liberation(s_etat_processus, s_connecteur);
  157:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  158:         return(NULL);
  159:     }
  160: 
  161:     serveur = (unsigned char *) (*(*l_element_courant).donnee).objet;
  162: 
  163:     // Dans le cas d'une base de données SQLite, seul le nom du fichier
  164:     // importe.
  165: 
  166:     if (strcmp(type_base, "SQLITE") == 0)
  167:     {
  168:         if ((*l_element_courant).suivant != NULL)
  169:         {
  170:             liberation(s_etat_processus, s_connecteur);
  171:             (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  172:             return(NULL);
  173:         }
  174: 
  175:         (*((struct_connecteur_sql *) (*s_connecteur).objet)).descripteur.sqlite
  176:                 = NULL;
  177: 
  178:         if (sqlite3_open_v2(serveur, &((*((struct_connecteur_sql *)
  179:                 (*s_connecteur).objet)).descripteur.sqlite),
  180:                 SQLITE_OPEN_READWRITE, NULL) != SQLITE_OK)
  181:         {
  182:             if ((*((struct_connecteur_sql *) (*s_connecteur).objet))
  183:                     .descripteur.sqlite != NULL)
  184:             {
  185:                 sqlite3_close((*((struct_connecteur_sql *)
  186:                         (*s_connecteur).objet)).descripteur.sqlite);
  187:             }
  188: 
  189:             liberation(s_etat_processus, s_connecteur);
  190:             (*s_etat_processus).erreur_execution = d_ex_erreur_sql;
  191:             return(NULL);
  192:         }
  193: 
  194:         return(s_connecteur);
  195:     }
  196:     else
  197:     {
  198: #       if !(defined(MYSQL_SUPPORT) || defined(POSTGRESQL_SUPPORT))
  199:         if ((*s_etat_processus).langue == 'F')
  200:         {
  201:             printf("+++Attention : Support de %s non compilé !\n", type_base);
  202:         }
  203:         else
  204:         {
  205:             printf("+++Warning : %s support not available !\n", type_base);
  206:         }
  207: #       endif
  208:     }
  209: 
  210: #   if defined(MYSQL_SUPPORT) || defined(POSTGRESQL_SUPPORT)
  211:     // Recherche du nom de la base de données
  212: 
  213:     l_element_courant = (*l_element_courant).suivant;
  214: 
  215:     if (l_element_courant == NULL)
  216:     {
  217:         liberation(s_etat_processus, s_connecteur);
  218:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  219:         return(NULL);
  220:     }
  221: 
  222:     if ((*(*l_element_courant).donnee).type != CHN)
  223:     {
  224:         liberation(s_etat_processus, s_connecteur);
  225:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  226:         return(NULL);
  227:     }
  228: 
  229:     base = (unsigned char *) (*(*l_element_courant).donnee).objet;
  230: 
  231:     // Recherche de l'utilisateur
  232: 
  233:     l_element_courant = (*l_element_courant).suivant;
  234: 
  235:     if (l_element_courant == NULL)
  236:     {
  237:         liberation(s_etat_processus, s_connecteur);
  238:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  239:         return(NULL);
  240:     }
  241: 
  242:     if ((*(*l_element_courant).donnee).type != CHN)
  243:     {
  244:         liberation(s_etat_processus, s_connecteur);
  245:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  246:         return(NULL);
  247:     }
  248: 
  249:     utilisateur = (unsigned char *) (*(*l_element_courant).donnee).objet;
  250: 
  251:     // Recherche du mot de passe
  252: 
  253:     l_element_courant = (*l_element_courant).suivant;
  254: 
  255:     if (l_element_courant == NULL)
  256:     {
  257:         liberation(s_etat_processus, s_connecteur);
  258:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  259:         return(NULL);
  260:     }
  261: 
  262:     if ((*(*l_element_courant).donnee).type != CHN)
  263:     {
  264:         liberation(s_etat_processus, s_connecteur);
  265:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  266:         return(NULL);
  267:     }
  268: 
  269:     mot_de_passe = (unsigned char *) (*(*l_element_courant).donnee).objet;
  270: 
  271:     // Recherche du port le cas échéant
  272: 
  273:     l_element_courant = (*l_element_courant).suivant;
  274: 
  275:     if (l_element_courant != NULL)
  276:     {
  277:         if ((*(*l_element_courant).donnee).type != INT)
  278:         {
  279:             liberation(s_etat_processus, s_connecteur);
  280:             (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  281:             return(NULL);
  282:         }
  283: 
  284:         if (((*((integer8 *) (*(*l_element_courant).donnee).objet)) < 0)
  285:                 || ((*((integer8 *) (*(*l_element_courant).donnee)
  286:                 .objet)) > 65535))
  287:         {
  288:             liberation(s_etat_processus, s_connecteur);
  289:             (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  290:             return(NULL);
  291:         }
  292: 
  293:         port = (unsigned int) (*((integer8 *)
  294:                 (*(*l_element_courant).donnee).objet));
  295: 
  296:         if ((*l_element_courant).suivant != NULL)
  297:         {
  298:             liberation(s_etat_processus, s_connecteur);
  299:             (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  300:             return(NULL);
  301:         }
  302:     }
  303:     else
  304:     {
  305:         port = 0;
  306:     }
  307: 
  308:     if (strcmp((*((struct_connecteur_sql *) (*s_connecteur).objet)).type,
  309:                 "MYSQL") == 0)
  310:     {
  311: #       ifdef MYSQL_SUPPORT
  312:         (*((struct_connecteur_sql *) (*s_connecteur).objet))
  313:                 .descripteur.mysql = NULL;
  314: 
  315:         if (((*((struct_connecteur_sql *) (*s_connecteur).objet))
  316:                 .descripteur.mysql = mysql_init(NULL)) == NULL)
  317:         {
  318:             liberation(s_etat_processus, s_connecteur);
  319:             (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
  320:             return(NULL);
  321:         }
  322: 
  323:         if (mysql_real_connect((*((struct_connecteur_sql *) (*s_connecteur)
  324:                 .objet)).descripteur.mysql, serveur, utilisateur, mot_de_passe,
  325:                 base, port, NULL, 0) == NULL)
  326:         {
  327:             mysql_close((*((struct_connecteur_sql *) (*s_connecteur).objet))
  328:                     .descripteur.mysql);
  329: 
  330:             liberation(s_etat_processus, s_connecteur);
  331:             (*s_etat_processus).erreur_execution = d_ex_erreur_sql;
  332:             return(NULL);
  333:         }
  334: #       else
  335:         if ((*s_etat_processus).langue == 'F')
  336:         {
  337:             printf("+++Attention : Support de MySQL non compilé !\n");
  338:         }
  339:         else
  340:         {
  341:             printf("+++Warning : MySQL support not available !\n");
  342:         }
  343: 
  344:         fflush(stdout);
  345: 
  346:         (*s_etat_processus).erreur_execution = d_ex_instruction_indisponible;
  347: #       endif
  348:     }
  349:     else if (strcmp((*((struct_connecteur_sql *) (*s_connecteur).objet)).type,
  350:                 "POSTGRESQL") == 0)
  351:     {
  352: #       ifdef POSTGRESQL_SUPPORT
  353:         if (port == 0)
  354:         {
  355:             sport = NULL;
  356:         }
  357:         else
  358:         {
  359:             if ((sport = malloc(32 * sizeof(unsigned char))) == NULL)
  360:             {
  361:                 liberation(s_etat_processus, s_connecteur);
  362:                 (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
  363:                 return(NULL);
  364:             }
  365: 
  366:             sprintf(sport, "%u", port);
  367:         }
  368: 
  369:         (*((struct_connecteur_sql *) (*s_connecteur).objet)).descripteur
  370:                 .postgresql = PQsetdbLogin(serveur, sport, NULL, NULL,
  371:                 base, utilisateur, mot_de_passe);
  372: 
  373:         free(sport);
  374: 
  375:         if (PQstatus((*((struct_connecteur_sql *) (*s_connecteur).objet))
  376:                 .descripteur.postgresql) != CONNECTION_OK)
  377:         {
  378:             PQfinish((*((struct_connecteur_sql *) (*s_connecteur).objet))
  379:                     .descripteur.postgresql);
  380: 
  381:             liberation(s_etat_processus, s_connecteur);
  382:             (*s_etat_processus).erreur_execution = d_ex_erreur_sql;
  383:             return(NULL);
  384:         }
  385: #       else
  386:         if ((*s_etat_processus).langue == 'F')
  387:         {
  388:             printf("+++Attention : Support de PostgreSQL non compilé !\n");
  389:         }
  390:         else
  391:         {
  392:             printf("+++Warning : PostgreSQL support not available !\n");
  393:         }
  394: 
  395:         fflush(stdout);
  396: 
  397:         (*s_etat_processus).erreur_execution = d_ex_instruction_indisponible;
  398: #       endif
  399:     }
  400:     else
  401:     {
  402:         liberation(s_etat_processus, s_connecteur);
  403:         (*s_etat_processus).erreur_execution = d_ex_argument_invalide;
  404:         return(NULL);
  405:     }
  406: #   endif
  407: 
  408:     return(s_connecteur);
  409: }
  410: 
  411: // vim: ts=4

CVSweb interface <joel.bertrand@systella.fr>