static void try_make_homedir (const char *fname) { const char *defhome = standard_homedir (); /* Create the directory only if the supplied directory name is the same as the default one. This way we avoid to create arbitrary directories when a non-default home directory is used. To cope with HOME, we do compare only the suffix if we see that the default homedir does start with a tilde. */ if ( opt.dry_run || opt.no_homedir_creation ) return; if ( #ifdef HAVE_W32_SYSTEM ( !compare_filenames (fname, defhome) ) #else ( *defhome == '~' && (strlen(fname) >= strlen (defhome+1) && !strcmp(fname+strlen(fname)-strlen(defhome+1), defhome+1 ) )) || (*defhome != '~' && !compare_filenames( fname, defhome ) ) #endif ) { if (gnupg_mkdir (fname, "-rwx")) log_info (_("can't create directory '%s': %s\n"), fname, strerror(errno) ); else if (!opt.quiet ) log_info (_("directory '%s' created\n"), fname); } }
/* * Check whether FNAME exists and ask if it's okay to overwrite an * existing one. * Returns: True: it's okay to overwrite or the file does not exist * False: Do not overwrite */ int overwrite_filep( const char *fname ) { if ( iobuf_is_pipe_filename (fname) ) return 1; /* Writing to stdout is always okay. */ if ( access( fname, F_OK ) ) return 1; /* Does not exist. */ if ( !compare_filenames (fname, NAME_OF_DEV_NULL) ) return 1; /* Does not do any harm. */ if (opt.answer_yes) return 1; if (opt.answer_no || opt.batch) return 0; /* Do not overwrite. */ tty_printf (_("File '%s' exists. "), fname); if (cpr_enabled ()) tty_printf ("\n"); if (cpr_get_answer_is_yes ("openfile.overwrite.okay", _("Overwrite? (y/N) ")) ) return 1; return 0; }
/* Check whether DIR is the default homedir. */ static int is_gnupg_default_homedir (const char *dir) { int result; char *a = make_absfilename (dir, NULL); char *b = make_absfilename (GNUPG_DEFAULT_HOMEDIR, NULL); result = !compare_filenames (a, b); xfree (b); xfree (a); return result; }
void try_make_homedir (const char *fname) { const char *defhome = standard_homedir (); /* Create the directory only if the supplied directory name is the same as the default one. This way we avoid to create arbitrary directories when a non-default home directory is used. To cope with HOME, we do compare only the suffix if we see that the default homedir does start with a tilde. */ if ( opt.dry_run || opt.no_homedir_creation ) return; if ( #ifdef HAVE_W32_SYSTEM ( !compare_filenames (fname, defhome) ) #else ( *defhome == '~' && (strlen(fname) >= strlen (defhome+1) && !strcmp(fname+strlen(fname)-strlen(defhome+1), defhome+1 ) )) || (*defhome != '~' && !compare_filenames( fname, defhome ) ) #endif ) { if (gnupg_mkdir (fname, "-rwx")) log_fatal ( _("can't create directory '%s': %s\n"), fname, strerror(errno) ); else if (!opt.quiet ) log_info ( _("directory '%s' created\n"), fname ); /* Note that we also copy a dirmngr.conf file here. This is because gpg is likely the first invoked tool and thus creates the directory. */ copy_options_file (fname, DIRMNGR_NAME); if (copy_options_file (fname, GPG_NAME)) log_info (_("WARNING: options in '%s'" " are not yet active during this run\n"), fname); } }
/* This is actually not used anymore but we keep a list of already * set extensions modules here. * * Here is the ancient comment: * Register an extension module. The last registered module will * be loaded first. A name may have a list of classes * appended; e.g: * mymodule.so(1:17,3:20,3:109) * means that this module provides digest algorithm 17 and public key * algorithms 20 and 109. This is only a hint but if it is there the * loader may decide to only load a module which claims to have a * requested algorithm. * * mainpgm is the path to the program which wants to load a module * it is only used in some environments. */ void register_cipher_extension( const char *mainpgm, const char *fname ) { EXTLIST r, el, intex; char *p, *pe; if( *fname != DIRSEP_C ) { /* do tilde expansion etc */ char *tmp; if( strchr(fname, DIRSEP_C) ) tmp = make_filename(fname, NULL); else tmp = make_filename(GNUPG_LIBDIR, fname, NULL); el = xmalloc_clear( sizeof *el + strlen(tmp) ); strcpy(el->name, tmp ); xfree(tmp); } else { el = xmalloc_clear( sizeof *el + strlen(fname) ); strcpy(el->name, fname ); } /* check whether we have a class hint */ if( (p=strchr(el->name,'(')) && (pe=strchr(p+1,')')) && !pe[1] ) *p = *pe = 0; /* check that it is not already registered */ intex = NULL; for(r = extensions; r; r = r->next ) { if( !compare_filenames(r->name, el->name) ) { log_info("extension `%s' already registered\n", el->name ); xfree(el); return; } } /* and register */ el->next = extensions; extensions = el; }
static void test_compare_filenames (void) { struct { const char *a; const char *b; int result; } tests[] = { { "", "", 0 }, { "", "a", -1 }, { "a", "", 1 }, { "a", "a", 0 }, { "a", "aa", -1 }, { "aa", "a", 1 }, { "a", "b", -1 }, #ifdef HAVE_W32_SYSTEM { "a", "A", 0 }, { "A", "a", 0 }, { "foo/bar", "foo\\bar", 0 }, { "foo\\bar", "foo/bar", 0 }, { "foo\\", "foo/", 0 }, { "foo/", "foo\\", 0 }, #endif /*HAVE_W32_SYSTEM*/ { NULL, NULL, 0} }; int testno, result; for (testno=0; tests[testno].a; testno++) { result = compare_filenames (tests[testno].a, tests[testno].b); result = result < 0? -1 : result > 0? 1 : 0; if (result != tests[testno].result) fail (testno); } }
/* Check whether the files NAME1 and NAME2 are identical. This is for example achieved by comparing the inode numbers of the files. */ int same_file_p (const char *name1, const char *name2) { int yes; /* First try a shortcut. */ if (!compare_filenames (name1, name2)) yes = 1; else { #ifdef HAVE_W32_SYSTEM HANDLE file1, file2; BY_HANDLE_FILE_INFORMATION info1, info2; #ifdef HAVE_W32CE_SYSTEM { wchar_t *wname = utf8_to_wchar (name1); if (wname) file1 = CreateFile (wname, 0, 0, NULL, OPEN_EXISTING, 0, NULL); else file1 = INVALID_HANDLE_VALUE; jnlib_free (wname); } #else file1 = CreateFile (name1, 0, 0, NULL, OPEN_EXISTING, 0, NULL); #endif if (file1 == INVALID_HANDLE_VALUE) yes = 0; /* If we can't open the file, it is not the same. */ else { #ifdef HAVE_W32CE_SYSTEM { wchar_t *wname = utf8_to_wchar (name2); if (wname) file2 = CreateFile (wname, 0, 0, NULL, OPEN_EXISTING, 0, NULL); else file2 = INVALID_HANDLE_VALUE; jnlib_free (wname); } #else file2 = CreateFile (name2, 0, 0, NULL, OPEN_EXISTING, 0, NULL); #endif if (file2 == INVALID_HANDLE_VALUE) yes = 0; /* If we can't open the file, it is not the same. */ else { yes = (GetFileInformationByHandle (file1, &info1) && GetFileInformationByHandle (file2, &info2) && info1.dwVolumeSerialNumber==info2.dwVolumeSerialNumber && info1.nFileIndexHigh == info2.nFileIndexHigh && info1.nFileIndexLow == info2.nFileIndexLow); CloseHandle (file2); } CloseHandle (file1); } #else /*!HAVE_W32_SYSTEM*/ struct stat info1, info2; yes = (!stat (name1, &info1) && !stat (name2, &info2) && info1.st_dev == info2.st_dev && info1.st_ino == info2.st_ino); #endif /*!HAVE_W32_SYSTEM*/ } return yes; }