17c478bd9Sstevel@tonic-gate 27c478bd9Sstevel@tonic-gate /* 37c478bd9Sstevel@tonic-gate * WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING 47c478bd9Sstevel@tonic-gate * 57c478bd9Sstevel@tonic-gate * Openvision retains the copyright to derivative works of 67c478bd9Sstevel@tonic-gate * this source code. Do *NOT* create a derivative of this 77c478bd9Sstevel@tonic-gate * source code before consulting with your legal department. 87c478bd9Sstevel@tonic-gate * Do *NOT* integrate *ANY* of this source code into another 97c478bd9Sstevel@tonic-gate * product before consulting with your legal department. 107c478bd9Sstevel@tonic-gate * 117c478bd9Sstevel@tonic-gate * For further information, read the top-level Openvision 127c478bd9Sstevel@tonic-gate * copyright which is contained in the top-level MIT Kerberos 137c478bd9Sstevel@tonic-gate * copyright. 147c478bd9Sstevel@tonic-gate * 157c478bd9Sstevel@tonic-gate * WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING WARNING 167c478bd9Sstevel@tonic-gate * 177c478bd9Sstevel@tonic-gate */ 187c478bd9Sstevel@tonic-gate 197c478bd9Sstevel@tonic-gate 207c478bd9Sstevel@tonic-gate /* 217c478bd9Sstevel@tonic-gate * Copyright 1993 OpenVision Technologies, Inc., All Rights Reserved 227c478bd9Sstevel@tonic-gate * 23*159d09a2SMark Phalan * $Header$ 247c478bd9Sstevel@tonic-gate */ 257c478bd9Sstevel@tonic-gate 267c478bd9Sstevel@tonic-gate #if !defined(lint) && !defined(__CODECENTER__) 27*159d09a2SMark Phalan static char *rcsid = "$Header$"; 287c478bd9Sstevel@tonic-gate #endif 297c478bd9Sstevel@tonic-gate 307c478bd9Sstevel@tonic-gate #include <sys/types.h> 317c478bd9Sstevel@tonic-gate #include <sys/file.h> 327c478bd9Sstevel@tonic-gate #include <fcntl.h> 337c478bd9Sstevel@tonic-gate #include <sys/stat.h> 347c478bd9Sstevel@tonic-gate #include <unistd.h> 3556a424ccSmp153739 #include <errno.h> 36*159d09a2SMark Phalan #include "server_internal.h" 377c478bd9Sstevel@tonic-gate #include <kadm5/admin.h> 387c478bd9Sstevel@tonic-gate #include <stdlib.h> 397c478bd9Sstevel@tonic-gate #include <stdio.h> 407c478bd9Sstevel@tonic-gate #include <string.h> 4156a424ccSmp153739 #ifdef HAVE_MEMORY_H 427c478bd9Sstevel@tonic-gate #include <memory.h> 4356a424ccSmp153739 #endif 4456a424ccSmp153739 #include "adm_proto.h" 457c478bd9Sstevel@tonic-gate #include <syslog.h> 467c478bd9Sstevel@tonic-gate #include <libintl.h> 477c478bd9Sstevel@tonic-gate 487c478bd9Sstevel@tonic-gate static char **word_list = NULL; /* list of word pointers */ 497c478bd9Sstevel@tonic-gate static char *word_block = NULL; /* actual word data */ 5056a424ccSmp153739 static unsigned int word_count = 0; /* number of words */ 5156a424ccSmp153739 527c478bd9Sstevel@tonic-gate 537c478bd9Sstevel@tonic-gate /* 547c478bd9Sstevel@tonic-gate * Function: word_compare 557c478bd9Sstevel@tonic-gate * 567c478bd9Sstevel@tonic-gate * Purpose: compare two words in the dictionary. 577c478bd9Sstevel@tonic-gate * 587c478bd9Sstevel@tonic-gate * Arguments: 597c478bd9Sstevel@tonic-gate * w1 (input) pointer to first word 607c478bd9Sstevel@tonic-gate * w2 (input) pointer to second word 617c478bd9Sstevel@tonic-gate * <return value> result of strcmp 627c478bd9Sstevel@tonic-gate * 637c478bd9Sstevel@tonic-gate * Requires: 647c478bd9Sstevel@tonic-gate * w1 and w2 to point to valid memory 657c478bd9Sstevel@tonic-gate * 667c478bd9Sstevel@tonic-gate */ 677c478bd9Sstevel@tonic-gate 687c478bd9Sstevel@tonic-gate static int 697c478bd9Sstevel@tonic-gate word_compare(const void *s1, const void *s2) 707c478bd9Sstevel@tonic-gate { 7156a424ccSmp153739 return (strcasecmp(*(const char **)s1, *(const char **)s2)); 727c478bd9Sstevel@tonic-gate } 737c478bd9Sstevel@tonic-gate 747c478bd9Sstevel@tonic-gate /* 757c478bd9Sstevel@tonic-gate * Function: init-dict 767c478bd9Sstevel@tonic-gate * 777c478bd9Sstevel@tonic-gate * Purpose: Initialize in memory word dictionary 787c478bd9Sstevel@tonic-gate * 797c478bd9Sstevel@tonic-gate * Arguments: 807c478bd9Sstevel@tonic-gate * none 8156a424ccSmp153739 * <return value> KADM5_OK on success errno on failure; 827c478bd9Sstevel@tonic-gate * (but success on ENOENT) 837c478bd9Sstevel@tonic-gate * 847c478bd9Sstevel@tonic-gate * Requires: 857c478bd9Sstevel@tonic-gate * If WORDFILE exists, it must contain a list of words, 867c478bd9Sstevel@tonic-gate * one word per-line. 877c478bd9Sstevel@tonic-gate * 887c478bd9Sstevel@tonic-gate * Effects: 897c478bd9Sstevel@tonic-gate * If WORDFILE exists, it is read into memory sorted for future 907c478bd9Sstevel@tonic-gate * use. If it does not exist, it syslogs an error message and returns 917c478bd9Sstevel@tonic-gate * success. 927c478bd9Sstevel@tonic-gate * 937c478bd9Sstevel@tonic-gate * Modifies: 947c478bd9Sstevel@tonic-gate * word_list to point to a chunck of allocated memory containing 957c478bd9Sstevel@tonic-gate * pointers to words 967c478bd9Sstevel@tonic-gate * word_block to contain the dictionary. 977c478bd9Sstevel@tonic-gate * 987c478bd9Sstevel@tonic-gate */ 997c478bd9Sstevel@tonic-gate 1007c478bd9Sstevel@tonic-gate int init_dict(kadm5_config_params *params) 1017c478bd9Sstevel@tonic-gate { 1027c478bd9Sstevel@tonic-gate int fd, 1037c478bd9Sstevel@tonic-gate len, 1047c478bd9Sstevel@tonic-gate i; 1057c478bd9Sstevel@tonic-gate char *p, 1067c478bd9Sstevel@tonic-gate *t; 1077c478bd9Sstevel@tonic-gate struct stat sb; 1087c478bd9Sstevel@tonic-gate 1097c478bd9Sstevel@tonic-gate if(word_list != NULL && word_block != NULL) 1107c478bd9Sstevel@tonic-gate return KADM5_OK; 1117c478bd9Sstevel@tonic-gate if (! (params->mask & KADM5_CONFIG_DICT_FILE)) { 112*159d09a2SMark Phalan /* Solaris Kerberos */ 11356a424ccSmp153739 krb5_klog_syslog(LOG_INFO, 1147c478bd9Sstevel@tonic-gate dgettext(TEXT_DOMAIN, 1157c478bd9Sstevel@tonic-gate "No dictionary file specified, continuing " 1167c478bd9Sstevel@tonic-gate "without one.")); 1177c478bd9Sstevel@tonic-gate return KADM5_OK; 1187c478bd9Sstevel@tonic-gate } 1197c478bd9Sstevel@tonic-gate if ((fd = open(params->dict_file, O_RDONLY)) == -1) { 1207c478bd9Sstevel@tonic-gate if (errno == ENOENT) { 121*159d09a2SMark Phalan /* Solaris Kerberos */ 12256a424ccSmp153739 krb5_klog_syslog(LOG_ERR, 1237c478bd9Sstevel@tonic-gate dgettext(TEXT_DOMAIN, 1247c478bd9Sstevel@tonic-gate "WARNING! Cannot find dictionary file %s, " 1257c478bd9Sstevel@tonic-gate "continuing without one."), params->dict_file); 1267c478bd9Sstevel@tonic-gate return KADM5_OK; 1277c478bd9Sstevel@tonic-gate } else 1287c478bd9Sstevel@tonic-gate return errno; 1297c478bd9Sstevel@tonic-gate } 1307c478bd9Sstevel@tonic-gate if (fstat(fd, &sb) == -1) 1317c478bd9Sstevel@tonic-gate return errno; 1327c478bd9Sstevel@tonic-gate if ((word_block = (char *) malloc(sb.st_size + 1)) == NULL) 1337c478bd9Sstevel@tonic-gate return errno; 1347c478bd9Sstevel@tonic-gate if (read(fd, word_block, sb.st_size) != sb.st_size) 1357c478bd9Sstevel@tonic-gate return errno; 1367c478bd9Sstevel@tonic-gate (void) close(fd); 1377c478bd9Sstevel@tonic-gate word_block[sb.st_size] = '\0'; 1387c478bd9Sstevel@tonic-gate 1397c478bd9Sstevel@tonic-gate p = word_block; 1407c478bd9Sstevel@tonic-gate len = sb.st_size; 1417c478bd9Sstevel@tonic-gate while(len > 0 && (t = memchr(p, '\n', len)) != NULL) { 1427c478bd9Sstevel@tonic-gate *t = '\0'; 1437c478bd9Sstevel@tonic-gate len -= t - p + 1; 1447c478bd9Sstevel@tonic-gate p = t + 1; 1457c478bd9Sstevel@tonic-gate word_count++; 1467c478bd9Sstevel@tonic-gate } 1477c478bd9Sstevel@tonic-gate if ((word_list = (char **) malloc(word_count * sizeof(char *))) == NULL) 1487c478bd9Sstevel@tonic-gate return errno; 1497c478bd9Sstevel@tonic-gate p = word_block; 1507c478bd9Sstevel@tonic-gate for (i = 0; i < word_count; i++) { 1517c478bd9Sstevel@tonic-gate word_list[i] = p; 1527c478bd9Sstevel@tonic-gate p += strlen(p) + 1; 1537c478bd9Sstevel@tonic-gate } 1547c478bd9Sstevel@tonic-gate qsort(word_list, word_count, sizeof(char *), word_compare); 1557c478bd9Sstevel@tonic-gate return KADM5_OK; 1567c478bd9Sstevel@tonic-gate } 1577c478bd9Sstevel@tonic-gate 1587c478bd9Sstevel@tonic-gate /* 1597c478bd9Sstevel@tonic-gate * Function: find_word 1607c478bd9Sstevel@tonic-gate * 1617c478bd9Sstevel@tonic-gate * Purpose: See if the specified word exists in the in-core dictionary 1627c478bd9Sstevel@tonic-gate * 1637c478bd9Sstevel@tonic-gate * Arguments: 1647c478bd9Sstevel@tonic-gate * word (input) word to search for. 1657c478bd9Sstevel@tonic-gate * <return value> WORD_NOT_FOUND if not in dictionary, 1667c478bd9Sstevel@tonic-gate * KADM5_OK if if found word 1677c478bd9Sstevel@tonic-gate * errno if init needs to be called and returns an 1687c478bd9Sstevel@tonic-gate * error 1697c478bd9Sstevel@tonic-gate * 1707c478bd9Sstevel@tonic-gate * Requires: 1717c478bd9Sstevel@tonic-gate * word to be a null terminated string. 1727c478bd9Sstevel@tonic-gate * That word_list and word_block besetup 1737c478bd9Sstevel@tonic-gate * 1747c478bd9Sstevel@tonic-gate * Effects: 1757c478bd9Sstevel@tonic-gate * finds word in dictionary. 1767c478bd9Sstevel@tonic-gate * Modifies: 1777c478bd9Sstevel@tonic-gate * nothing. 1787c478bd9Sstevel@tonic-gate * 1797c478bd9Sstevel@tonic-gate */ 1807c478bd9Sstevel@tonic-gate 1817c478bd9Sstevel@tonic-gate int 1827c478bd9Sstevel@tonic-gate find_word(const char *word) 1837c478bd9Sstevel@tonic-gate { 1847c478bd9Sstevel@tonic-gate char **value; 1857c478bd9Sstevel@tonic-gate 1867c478bd9Sstevel@tonic-gate if(word_list == NULL || word_block == NULL) 1877c478bd9Sstevel@tonic-gate return WORD_NOT_FOUND; 1887c478bd9Sstevel@tonic-gate if ((value = (char **) bsearch(&word, word_list, word_count, sizeof(char *), 1897c478bd9Sstevel@tonic-gate word_compare)) == NULL) 1907c478bd9Sstevel@tonic-gate return WORD_NOT_FOUND; 1917c478bd9Sstevel@tonic-gate else 1927c478bd9Sstevel@tonic-gate return KADM5_OK; 1937c478bd9Sstevel@tonic-gate } 1947c478bd9Sstevel@tonic-gate 1957c478bd9Sstevel@tonic-gate /* 1967c478bd9Sstevel@tonic-gate * Function: destroy_dict 1977c478bd9Sstevel@tonic-gate * 1987c478bd9Sstevel@tonic-gate * Purpose: destroy in-core copy of dictionary. 1997c478bd9Sstevel@tonic-gate * 2007c478bd9Sstevel@tonic-gate * Arguments: 2017c478bd9Sstevel@tonic-gate * none 2027c478bd9Sstevel@tonic-gate * <return value> none 2037c478bd9Sstevel@tonic-gate * Requires: 2047c478bd9Sstevel@tonic-gate * nothing 2057c478bd9Sstevel@tonic-gate * Effects: 2067c478bd9Sstevel@tonic-gate * frees up memory occupied by word_list and word_block 2077c478bd9Sstevel@tonic-gate * sets count back to 0, and resets the pointers to NULL 2087c478bd9Sstevel@tonic-gate * 2097c478bd9Sstevel@tonic-gate * Modifies: 2107c478bd9Sstevel@tonic-gate * word_list, word_block, and word_count. 2117c478bd9Sstevel@tonic-gate * 2127c478bd9Sstevel@tonic-gate */ 2137c478bd9Sstevel@tonic-gate 2147c478bd9Sstevel@tonic-gate void 2157c478bd9Sstevel@tonic-gate destroy_dict(void) 2167c478bd9Sstevel@tonic-gate { 2177c478bd9Sstevel@tonic-gate if(word_list) { 2187c478bd9Sstevel@tonic-gate free(word_list); 2197c478bd9Sstevel@tonic-gate word_list = NULL; 2207c478bd9Sstevel@tonic-gate } 2217c478bd9Sstevel@tonic-gate if(word_block) { 2227c478bd9Sstevel@tonic-gate free(word_block); 2237c478bd9Sstevel@tonic-gate word_block = NULL; 2247c478bd9Sstevel@tonic-gate } 2257c478bd9Sstevel@tonic-gate if(word_count) 2267c478bd9Sstevel@tonic-gate word_count = 0; 2277c478bd9Sstevel@tonic-gate return; 2287c478bd9Sstevel@tonic-gate } 229