Ejemplo n.º 1
0
/*--------------------------------------------------------------------------*/
int dictionary_set(dictionary * d, char * key, char * val)
{
	int			i ;
	unsigned	hash ;

	if (d==NULL || key==NULL) return -1 ;

	/* Compute hash for this key */
	hash = dictionary_hash(key) ;
	/* Find if value is already in dictionary */
	if (d->n>0) {
		for (i=0 ; i<d->size ; i++) {
	    if (d->key[i]==NULL)
		continue ;
			if (hash==d->hash[i]) { /* Same hash value */
				if (!strcmp(key, d->key[i])) {	 /* Same key */
					/* Found a value: modify and return */
					if (d->val[i]!=NULL)
						free(d->val[i]);
		    d->val[i] = val ? xstrdup(val) : NULL ;
		    /* Value has been modified: return */
					return 0 ;
				}
			}
		}
	}
	/* Add a new value */
	/* See if dictionary needs to grow */
	if (d->n==d->size) {

		/* Reached maximum size: reallocate dictionary */
		d->val  = (char **)mem_double(d->val,  d->size * sizeof(char*)) ;
		d->key  = (char **)mem_double(d->key,  d->size * sizeof(char*)) ;
		d->hash = (unsigned int *)mem_double(d->hash, d->size * sizeof(unsigned)) ;
	if ((d->val==NULL) || (d->key==NULL) || (d->hash==NULL)) {
	    /* Cannot grow dictionary */
	    return -1 ;
	}
		/* Double size */
		d->size *= 2 ;
	}

    /* Insert key in the first empty slot */
    for (i=0 ; i<d->size ; i++) {
	if (d->key[i]==NULL) {
	    /* Add key here */
	    break ;
	}
    }
	/* Copy key */
	d->key[i]  = xstrdup(key);
    d->val[i]  = val ? xstrdup(val) : NULL ;
	d->hash[i] = hash;
	d->n ++ ;
	return 0 ;
}
Ejemplo n.º 2
0
/*--------------------------------------------------------------------------*/
void dictionary_unset(dictionary* d, const char* key)
{
    unsigned    hash ;
    size_t      i ;

    if (key == NULL)
    {
        return;
    }

    hash = dictionary_hash(key);

    for (i=0 ; i<(size_t)d->size ; i++)
    {
        if (d->key[i]==NULL)
        {
            continue ;
        }

        /* Compare hash */
        if (hash==d->hash[i])
        {
            /* Compare string, to avoid hash collisions */
            if (!strcmp(key, d->key[i]))
            {
                /* Found key */
                break ;
            }
        }
    }

    if (i>=(size_t)d->size)
        /* Key not found */
    {
        return ;
    }

    free(d->key[i]);
    d->key[i] = NULL ;

    if (d->val[i]!=NULL)
    {
        free(d->val[i]);
        d->val[i] = NULL ;
    }

    d->hash[i] = 0 ;
    d->n -- ;
    return ;
}
Ejemplo n.º 3
0
int dictionary_getbufsize(dictionary * d, char * key)
{
	unsigned	hash ;
	int			i ;
	hash = dictionary_hash(key);
	for (i=0 ; i<d->size ; i++) {
        	if (d->key[i]==NULL)
            		continue ;
        	/* Compare hash */ 
		if (hash==d->hash[i]) {
            		/* Compare string, to avoid hash collisions */ 
            		if (!strcmp(key, d->key[i])) {
				return d->bufsize[i] ;
	    		}
		}
	}
	return 0 ;
}
Ejemplo n.º 4
0
/*--------------------------------------------------------------------------*/
void dictionary_unset
    (LPDICTIONARY lpDict,       // Ptr to workspace dictionary
     LPWCHAR      lpwKey)

{
    UINT hash;
    int  i;

    Assert (lpDict NE NULL);
    Assert (lpwKey NE NULL);

    // Hash the key
    hash = dictionary_hash (lpwKey);

    for (i = 0; i < lpDict->size; i++)
    if (lpDict->key[i] NE NULL)
    {
        /* Compare hash */
        if (hash EQ lpDict->hash[i])
        {
            /* Compare string, to avoid hash collisions */
            if (!lstrcmpW (lpwKey, lpDict->key[i]))
                /* Found key */
                break;
        } // End IF
    } // End FOR/IF

    if (i >= lpDict->size)
        /* Key not found */
        return;

    // Free the key
    free (lpDict->key[i]); lpDict->key[i] = NULL;

    // Free values if they were allocated
    if (lpDict->val[i] NE NULL)
    {
        free (lpDict->val[i]);
        lpDict->val[i] = NULL;
    } // End IF

    lpDict->hash[i] = 0;
    lpDict->n--;
} // End dictionary_unset
Ejemplo n.º 5
0
/*--------------------------------------------------------------------------*/
static const char * dictionary_get(dictionary * d, const char * key, const char * def)
{
    unsigned    hash ;
    int         i ;

    hash = dictionary_hash(key);
    for (i=0 ; i<d->size ; i++) {
        if (d->key==NULL)
            continue ;
        /* Compare hash */
        if (hash==d->hash[i]) {
            /* Compare string, to avoid hash collisions */
            if (!strcmp(key, d->key[i])) {
                return d->val[i] ;
            }
        }
    }
    return def ;
}
Ejemplo n.º 6
0
static t_hash_element *dictionary_get_element(t_dictionary *self, char *key) {
    unsigned int key_hash = dictionary_hash(key, strlen(key));
    int index = key_hash % self->table_max_size;

    t_hash_element *element = self->elements[index];

    if (element == NULL) {
        return NULL;
    }

    do {

        if (element->hashcode == key_hash) {
            return element;
        }

    } while ((element = element->next) != NULL);

    return NULL;
}
/*--------------------------------------------------------------------------*/
static void
dictionary_unset (dictionary * d, char * key)
{
    unsigned    hash;
    int         i;

    hash = dictionary_hash (key);

    for (i = 0; i < d->size; i++)
    {
	if (!d->key[i])
	    continue;

	/* Compare hash */
	if (hash == d->hash[i])
      	{
	    /* Compare string, to avoid hash collisions */
	    if (!strcmp (key, d->key[i]))
	    {
		/* Found key */
		break;
	    }
	}
    }

    if (i >= d->size)
	/* Key not found */
	return;

    free (d->key[i]);

    d->key[i] = NULL;
    if (d->val[i])
    {
	free (d->val[i]);
	d->val[i] = NULL;
    }

    d->hash[i] = 0;
    d->n --;
}
Ejemplo n.º 8
0
int iniparser_find_entry(
	dictionary	*	ini,
	char		*	entry
)
{
	int		i ;
	int		hash ;
	int		found ;

	found = 0 ;
	hash = dictionary_hash(entry);
	for (i=0 ; i<ini->n ; i++) {
		if (hash==ini->hash[i]) {
			if (!strcmp(entry, ini->key[i])) {
				found = 1 ;
				break ;
			}
		}
	}
	return found ;
}
Ejemplo n.º 9
0
/*--------------------------------------------------------------------------*/
LPWCHAR dictionary_get
    (LPDICTIONARY lpDict,       // Ptr to workspace dictionary
     LPWCHAR      lpwKey,
     LPWCHAR      lpwDef,
     LPINT        lpIndex)      // Ptr to index on output (may be NULL)

{
    UINT hash;
    int  i;

    Assert (lpDict NE NULL);

    // If it's valid, ...
    if (lpIndex NE NULL)
        // Initialize it
        *lpIndex = -1;

    // Hash the key
    hash = dictionary_hash (lpwKey);

    for (i = 0; i < lpDict->size; i++)
    if (lpDict->key[i] NE NULL)
    {
        /* Compare hash */
        if (hash EQ lpDict->hash[i])
        {
            /* Compare string, to avoid hash collisions */
            if (!lstrcmpW (lpwKey, lpDict->key[i]))
            {
                if (lpIndex NE NULL)
                    *lpIndex = i;

                return lpDict->val[i];
            } // End IF
        } // End IF
    } // End FOR/IF

    return lpwDef;
} // End dictionary_get
Ejemplo n.º 10
0
static void *dictionary_remove_element(t_dictionary *self, char *key) {
    unsigned int key_hash = dictionary_hash(key, strlen(key));
    int index = key_hash % self->table_max_size;

    t_hash_element *element = self->elements[index];

    if (element == NULL) {
        return NULL;
    }

    if (element->hashcode == key_hash) {
        void *data = element->data;
        self->elements[index] = element->next;
        if (self->elements[index] == NULL) {
            self->table_current_size--;
        }
        free(element->key);
        free(element);
        return data;
    }

    while (element->next != NULL) {

        if (element->next->hashcode == key_hash) {
            void *data = element->next->data;
            t_hash_element *aux = element->next;
            element->next = element->next->next;
            free(aux->key);
            free(aux);
            return data;
        }

        element = element->next;
    }

    return NULL;
}
Ejemplo n.º 11
0
int main(int argc, char **argv) {
        int port = 5586,
            notification_timeout = 5,
            config_preceeds = 1,
            sockfd,
            newsockfd,
            c;

        socklen_t clilen;
        char msg[256];
        char buffer[256];
        struct sockaddr_in serv_addr, cli_addr;

        while (1) {
                static struct option long_options[] =
                {
                        /* These options don't set a flag.
                         * We distinguish them by their indices. */
                        {"port",    required_argument, 0, 'p'},
                        {"timeout", required_argument, 0, 't'},
                        {"help",    no_argument,       0, 'h'},
                        {0, 0, 0, 0}
                };
                /* getopt_long stores the option index here. */
                int option_index = 0;

                c = getopt_long (argc, argv, "hp:t:",
                                long_options, &option_index);

                /* Detect the end of the options. */
                if (c == -1)
                        break;

                switch (c)
                {
                        case 0:
                                /* If this option set a flag, do nothing else now. */
                                if (long_options[option_index].flag != 0)
                                        break;
                                printf ("option %s", long_options[option_index].name);
                                if (optarg)
                                        printf (" with arg %s", optarg);
                                printf ("\n");
                                break;

                        case 'p':
                                port = atoi(optarg);
                                config_preceeds = 0;
                                break;

                        case 't':
                                notification_timeout = atoi(optarg);
                                config_preceeds = 0;
                                break;

                        case 'h':
                                printf ("Usage:\n");
                                printf ("%s [-h] [-p port_number] [-t notification_timeout]\n", argv[0]);
                                exit(EXIT_SUCCESS);

                        case '?':
                                /* getopt_long already printed an error message. */
                                break;

                        default:
                                printf("Unkown parameter. Exiting.\n");
                                exit(EXIT_FAILURE);
                }
        }

        /* Our process ID and Session ID */
        pid_t pid, sid, pid_found;

        dictionary *dict;

        /* Fork off the parent process */
        pid = fork();
        if (pid < 0) {
                printf("Cannot fork the daemon. Exiting...\n");
                exit(EXIT_FAILURE);
        }
        /* If we got a good PID, then
         *            we can exit the parent process. */
        if (pid > 0) {
                exit(EXIT_SUCCESS);
        }

        /* Change the file mode mask */
        umask(0);

        openlog ("notifmed", LOG_CONS | LOG_PID | LOG_NDELAY, LOG_LOCAL0);
        syslog (LOG_INFO, "Program started by user %d", getuid ());

        if (config_preceeds) {
                char * home = getenv("HOME");
                char * home_path_config = malloc(snprintf(NULL, 0, "%s/%s", home, ".notifmedrc") + 1);
                sprintf(home_path_config, "%s/%s", home, ".notifmedrc");

                if (file_exists(home_path_config)) {
                        dict = iniparser_load(home_path_config);
                } else if (file_exists("/etc/notifmed.rc")) {
                        dict = iniparser_load("/etc/notifmed.rc");
                        /* a config file could also be given as argument
                           } else if (file_exists()) {
                           dict = iniparser_load();*/
                } else {
                        syslog (LOG_INFO, "No configuration file found.");
                        syslog (LOG_INFO, "Using defaults:");
                        syslog (LOG_INFO, "    port = 5586 ; notification_timeout = 5");
                }

                if (!dict) {
                        syslog (LOG_ERR, "Dictionary configuration file problem.");
                        closelog();
                        exit(EXIT_FAILURE);
                }

                int i;
                unsigned int hh=dictionary_hash("server");
                for ( i=0 ; (i<dict->n) && (hh!=dict->hash[i]) ; i++);
                // No "server" section found
                if( i == dict->n ) {
                        syslog (LOG_INFO, "No server section found.");
                        syslog (LOG_INFO, "Using defaults:");
                        syslog (LOG_INFO, "    port = 5586 ; notification_timeout = 5");
                }

                for ( i++ ; ( i < dict->n ) && strncmp(dict->key[i],"server:",6) == 0 ; i++ ) {
                        if (strcmp(dict->key[i],"server:port") == 0) {
                                port = atoi(dict->val[i]);
                        } else if (strcmp(dict->key[i],"server:notification_timeout") == 0) {
                                notification_timeout = atoi(dict->val[i]);
                        }
                }
        }
        syslog (LOG_INFO, "Config found: port=%i - notification_timeout=%i", port, notification_timeout);

        /* Create a new SID for the child process */
        sid = setsid();
        if (sid < 0) {
                syslog (LOG_ERR, "Cannot create a new SID.");
                closelog();
                exit(EXIT_FAILURE);
        }

        // Preparing the network part
        sockfd = socket(AF_INET, SOCK_STREAM, 0);
        if (sockfd < 0) {
                syslog (LOG_ERR, "Cannot open the socket.");
                closelog();
                exit(EXIT_FAILURE);
        }

        bzero((char *) &serv_addr, sizeof(serv_addr));
        serv_addr.sin_family = AF_INET;
        serv_addr.sin_addr.s_addr = INADDR_ANY;
        serv_addr.sin_port = htons(port);

        if (bind(sockfd, (struct sockaddr *) &serv_addr, sizeof(serv_addr)) < 0) {
                syslog (LOG_ERR, "Cannot bind the socket.");
                closelog();
                exit(EXIT_FAILURE);
        }

        listen(sockfd,5);
        clilen = sizeof(cli_addr);

        /* Change the current working directory */
        if ((chdir("/")) < 0) {
                syslog (LOG_ERR, "Cannot create a new SID.");
                closelog();
                exit(EXIT_FAILURE);
        }

        /* Close out the standard file descriptors */
        close(STDIN_FILENO);
        close(STDOUT_FILENO);
        close(STDERR_FILENO);

        NotifyNotification *n;
        notify_init("Initialization");
        n = notify_notification_new ("notifmed","Initialized!\nMonitoring for client requests...", NULL);
        notify_notification_set_timeout(n, notification_timeout * 1000); //3 seconds
        if (!notify_notification_show (n, NULL)) {
                g_error("Failed to send notification.\n");
                return 1;
        }
        g_object_unref(G_OBJECT(n));

        /* The Big Loop */
        while (1) {
                newsockfd = accept(sockfd, (struct sockaddr *) &cli_addr, &clilen);
                if (newsockfd < 0) {
                        syslog (LOG_ERR, "Cannot accept messages.");
                        closelog();
                        close(newsockfd);
                        close(sockfd);
                        exit(EXIT_FAILURE);
                }

                bzero(buffer,256);

                n = read(newsockfd,buffer,255);
                if (n < 0) {
                        syslog (LOG_ERR, "Error reading from the socket.");
                        closelog();
                        close(newsockfd);
                        close(sockfd);
                        exit(EXIT_FAILURE);
                }

                syslog (LOG_INFO, "Here is the message: %s\n",buffer);
                pid_found = getProcessID((char *)buffer);

                sprintf(msg,"Monitoring process: %s (PID: %i)",buffer, pid_found);
                n = notify_notification_new ("notifmed",msg, NULL);
                notify_notification_set_timeout(n, notification_timeout * 1000); //3 seconds
                if (!notify_notification_show (n, NULL)) {
                        g_error("Failed to send notification.\n");
                        return 1;
                }

                n = write(newsockfd,msg,255);

                if (n < 0) {
                        syslog (LOG_ERR, "Error writing to the socket.");
                        closelog();
                        close(newsockfd);
                        close(sockfd);
                        exit(EXIT_FAILURE);
                }

                //sleep(3); /* wait 3 seconds */
        }

        close(newsockfd);
        close(sockfd);
        closelog();
        exit(EXIT_SUCCESS);
}
Ejemplo n.º 12
0
/*--------------------------------------------------------------------------*/
int dictionary_set(dictionary* d, const char* key, const char* val)
{
    size_t      i ;
    unsigned    hash ;

    if (d==NULL || key==NULL)
    {
        return -1 ;
    }

    /* Compute hash for this key */
    hash = dictionary_hash(key) ;

    /* Find if value is already in dictionary */
    if (d->n>0)
    {
        for (i=0 ; i<(size_t)d->size ; i++)
        {
            if (d->key[i]==NULL)
            {
                continue ;
            }

            if (hash==d->hash[i])   /* Same hash value */
            {
                if (!strcmp(key, d->key[i]))     /* Same key */
                {
                    /* Found a value: modify and return */
                    if (d->val[i]!=NULL)
                    {
                        free(d->val[i]);
                    }

                    d->val[i] = val ? xstrdup(val) : NULL ;
                    /* Value has been modified: return */
                    return 0 ;
                }
            }
        }
    }

    /* Add a new value */
    /* See if dictionary needs to grow */
    if (d->n==d->size)
    {

        /* Reached maximum size: reallocate dictionary */
        d->val  = (char** )mem_double(d->val,  d->size * sizeof *d->val) ;
        d->key  = (char** )mem_double(d->key,  d->size * sizeof *d->key) ;
        d->hash = (unsigned* )mem_double(d->hash, d->size * sizeof *d->hash) ;

        if ((d->val==NULL) || (d->key==NULL) || (d->hash==NULL))
        {
            /* Cannot grow dictionary */
            return -1 ;
        }

        /* Double size */
        d->size *= 2 ;
    }

    /* Insert key in the first empty slot. Start at d->n and wrap at
       d->size. Because d->n < d->size this will necessarily
       terminate. */
    for (i=d->n ; d->key[i] ; )
    {
        if(++i == (size_t)d->size)
        {
            i = 0;
        }
    }

    /* Copy key */
    d->key[i]  = xstrdup(key);
    d->val[i]  = val ? xstrdup(val) : NULL ;
    d->hash[i] = hash;
    d->n ++ ;
    return 0 ;
}
Ejemplo n.º 13
0
/*--------------------------------------------------------------------------*/
dictionary_value* dictionary_set(dictionary * d, const char * key, char * val, int type, void* ptr,void (*cb)(void))
{
  int i;
  unsigned  hash;

  if (d==NULL || key==NULL)
    return NULL ;

  /* Compute hash for this key */
  hash = dictionary_hash(key) ;
  /* Find if value is already in dictionary */
  if (d->n>0) {
    for (i=0 ; i<d->size ; i++) {
      if (d->key[i]==NULL)
        continue ;
      if (hash==d->hash[i]) { /* Same hash value */
        if (!strcmp(key, d->key[i])) { /* Same key */
          /* Found a value: modify and return */
          if (d->values[i].val!=NULL)
            free(d->values[i].val);

          d->values[i].val  = (val != NULL) ? xstrdup(val) : NULL ;
          /* Value has been modified: return */
          return &d->values[i];
        }
      }
    }
  }

  /* Add a new value */
  /* See if dictionary needs to grow */
  if (d->n==d->size) {
    /* Reached maximum size: reallocate dictionary */
    d->values = (dictionary_value *)mem_double(d->values,  d->size * sizeof(dictionary_value*)) ;
    d->key    = (char **)mem_double(d->key,  d->size * sizeof(char*)) ;
    d->hash   = (unsigned int *)mem_double(d->hash, d->size * sizeof(unsigned)) ;
    if ((d->values==NULL) || (d->key==NULL) || (d->hash==NULL)) {
        /* Cannot grow dictionary */
        return NULL;
    }
    /* Double size */
    d->size *= 2 ;
  }

  /* Insert key in the first empty slot */
  for (i=0 ; i<d->size ; i++) {
    if (d->key[i]==NULL) {
        /* Add key here */
        break ;
    }
  }
  /* Copy key */
  d->key[i]         = xstrdup(key);
  d->values[i].val  = (val != NULL) ? xstrdup(val) : NULL;
  d->values[i].type = type;
  d->values[i].callback = NULL;
  d->values[i].rw = 0;
  d->values[i].scope = -1;
  d->values[i].ptr  = ptr;
  d->hash[i]        = hash;
  d->n ++ ;

  return &d->values[i] ;
}
Ejemplo n.º 14
0
/*--------------------------------------------------------------------------*/
int dictionary_set
    (LPDICTIONARY lpDict,       // Ptr to workspace dictionary
     LPWCHAR      lpwKey,
     LPWCHAR      lpwVal)

{
    int  i;
    UINT hash;

    Assert (lpDict NE NULL);
    Assert (lpwKey NE NULL);

    // Hash the key
    hash = dictionary_hash (lpwKey);

    /* Find if value is already in dictionary */
    if (lpDict->n > 0)
    {
        for (i = 0; i < lpDict->size; i++)
        if (lpDict->key[i] NE NULL)
        {
            if (hash EQ lpDict->hash[i])
            { /* Same hash value */
                if (!lstrcmpW (lpwKey, lpDict->key[i]))
                {   /* Same key */
                    /* Found a value: modify and return */
                    if (lpwVal EQ NULL
                     || (lpDict->inifile <= lpwVal
                      &&                    lpwVal < (lpDict->inifile + lpDict->size)))
                        lpDict->val[i] = lpwVal;
                    else
                    {
                        if (lpDict->val[i] NE NULL)
                        {
                            free (lpDict->val[i]); lpDict->val[i] = NULL;
                        } // End IF

                        if (lpwVal NE NULL)
                        {
                            lpwVal = strdupW (lpwVal);
                            if (lpwVal EQ NULL)
                                return -1;
                        } // End IF

                        lpDict->val[i] = lpwVal;
                    } // End IF/ELSE

                    /* Value has been modified: return */
                    return 0;
                } // End IF
            } // End IF
        } // End FOR/IF
    } // End IF

    /* Add a new value */
    /* See if dictionary needs to grow */
    if (lpDict->n EQ lpDict->size)
    {
        LPWCHAR *val;               // Ptr to list of string values
        LPWCHAR *key;               // Ptr to list of string keys
        LPUINT   hash;              // Ptr to list of hash values for keys

        /* Reached maximum size: reallocate dictionary */
        val  = (LPWCHAR *) mem_double (lpDict->val,  lpDict->size * sizeof (*lpDict->val));
        key  = (LPWCHAR *) mem_double (lpDict->key,  lpDict->size * sizeof (*lpDict->key));
        hash = (LPUINT)    mem_double (lpDict->hash, lpDict->size * sizeof (*lpDict->hash));
        if ((val EQ NULL) || (key EQ NULL) || (hash EQ NULL))
        {
            // Replace the values that succeeded in doubling
            if (val  NE NULL) lpDict->val  = val;
            if (key  NE NULL) lpDict->key  = key;
            if (hash NE NULL) lpDict->hash = hash;

            /* Cannot grow dictionary */
            return -1;
        } // End IF

        lpDict->val  = val;
        lpDict->key  = key;
        lpDict->hash = hash;

        /* Double size */
        lpDict->size *= 2;
    } // End IF

    /* Insert key in the first empty slot */
    for (i = 0; i < lpDict->size; i++)
    if (lpDict->key[i] EQ NULL)
        /* Add key here */
        break;

    // If the key is NULL or within the file contents, it can be
    //   stored directly; otherwise it must be duplicated.
    if (lpwKey EQ NULL
     || (lpDict->inifile <= lpwKey
      &&                    lpwKey < (lpDict->inifile + lpDict->size)))
        lpDict->key[i] = lpwKey;
    else
    {
        lpDict->key[i] = strdupW (lpwKey);
        if (lpDict->key[i] EQ NULL)
            return -1;
    } // End IF/ELSE

    // If the value is NULL or within the file contents, it can be
    //   stored directly; otherwise it must be duplicated.
    if (lpwVal EQ NULL
     || (lpDict->inifile <= lpwVal
      &&                    lpwVal < (lpDict->inifile + lpDict->size)))
        lpDict->val[i] = lpwVal;
    else
    {
        if (lpDict->val[i] NE NULL)
        {
            free (lpDict->val[i]); lpDict->val[i] = NULL;
        } // End IF

        lpDict->val[i] = strdupW (lpwVal);
        if (lpDict->val[i] EQ NULL)
            return -1;
    } // End IF/ELSE

    lpDict->hash[i] = hash;
    lpDict->n++;

    return 0;
} // End dictionary_set
Ejemplo n.º 15
0
/*--------------------------------------------------------------------------*/
static void
dictionary_set (dictionary * d, char * key, char * val)
{
    int         i;
    unsigned    hash;

    if (!d || !key)
	return;

    /* Compute hash for this key */
    hash = dictionary_hash (key);

    /* Find if value is already in blackboard */
    if (d->n > 0)
    {
	for (i = 0; i < d->size; ++i)
	{
	    if (!d->key[i])
		continue;

	    if (hash == d->hash[i])
    	    {
		/* Same hash value */
	    	if (!strcmp (key, d->key[i]))
		{
		    /* Same key */
		    /* Found a value: modify and return */
		    if (d->val[i])
			free (d->val[i]);

		    d->val[i] = val ? strdup (val) : NULL;
		    /* Value has been modified: return */
		    return;
		}
	    }
	}
    }

    /* Add a new value */
    /* See if dictionary needs to grow */
    if (d->n == d->size)
    {
	/* Reached maximum size: reallocate blackboard */
	d->val  = (char **) mem_double (d->val,  d->size * sizeof (char*));
	d->key  = (char **) mem_double (d->key,  d->size * sizeof (char*));
	d->hash = (unsigned int *) mem_double (d->hash,
					       d->size * sizeof (unsigned));

	/* Double size */
	d->size *= 2;
    }

    /* Insert key in the first empty slot */
    for (i = 0; i < d->size; ++i)
    {
	if (!d->key[i])
	{
	    /* Add key here */
    	    break;
	}
    }

    /* Copy key */
    d->key[i]  = strdup (key);
    d->val[i]  = val ? strdup (val) : NULL;
    d->hash[i] = hash;
    ++d->n;
}
Ejemplo n.º 16
0
void Test_dictionary_hash(CuTest *tc)
{
    /* NULL test */
    CuAssertIntEquals(tc, 0, dictionary_hash(NULL));
}