static void file_expand_directory(bContext *C) { SpaceFile *sfile = CTX_wm_space_file(C); if (sfile->params) { /* TODO, what about // when relbase isn't valid? */ if (G.relbase_valid && BLI_path_is_rel(sfile->params->dir)) { BLI_path_abs(sfile->params->dir, G.main->name); } else if (sfile->params->dir[0] == '~') { char tmpstr[sizeof(sfile->params->dir) - 1]; BLI_strncpy(tmpstr, sfile->params->dir + 1, sizeof(tmpstr)); BLI_join_dirfile(sfile->params->dir, sizeof(sfile->params->dir), BLI_getDefaultDocumentFolder(), tmpstr); } else if (sfile->params->dir[0] == '\0') #ifndef WIN32 { sfile->params->dir[0] = '/'; sfile->params->dir[1] = '\0'; } #else { get_default_root(sfile->params->dir); } /* change "C:" --> "C:\", [#28102] */ else if ((isalpha(sfile->params->dir[0]) && (sfile->params->dir[1] == ':')) && (sfile->params->dir[2] == '\0')) { sfile->params->dir[2] = '\\'; sfile->params->dir[3] = '\0'; } #endif }
ImBuf *IMB_testiffname(const char *filepath, int flags) { ImBuf *ibuf; int file; char filepath_tx[IB_FILENAME_SIZE]; char colorspace[IM_MAX_SPACE] = "\0"; BLI_assert(!BLI_path_is_rel(filepath)); imb_cache_filename(filepath_tx, filepath, flags); file = BLI_open(filepath_tx, O_BINARY | O_RDONLY, 0); if (file == -1) return NULL; ibuf = IMB_loadifffile(file, filepath, flags | IB_test | IB_multilayer, colorspace, filepath_tx); if (ibuf) { BLI_strncpy(ibuf->name, filepath, sizeof(ibuf->name)); BLI_strncpy(ibuf->cachename, filepath_tx, sizeof(ibuf->cachename)); } close(file); return ibuf; }
ImBuf *IMB_loadiffname(const char *filepath, int flags, char colorspace[IM_MAX_SPACE]) { ImBuf *ibuf; int file, a; char filepath_tx[IB_FILENAME_SIZE]; BLI_assert(!BLI_path_is_rel(filepath)); imb_cache_filename(filepath_tx, filepath, flags); file = BLI_open(filepath_tx, O_BINARY | O_RDONLY, 0); if (file == -1) return NULL; ibuf = IMB_loadifffile(file, filepath, flags, colorspace, filepath_tx); if (ibuf) { BLI_strncpy(ibuf->name, filepath, sizeof(ibuf->name)); BLI_strncpy(ibuf->cachename, filepath_tx, sizeof(ibuf->cachename)); for (a = 1; a < ibuf->miptot; a++) BLI_strncpy(ibuf->mipmap[a - 1]->cachename, filepath_tx, sizeof(ibuf->cachename)); if (flags & IB_fields) IMB_de_interlace(ibuf); } close(file); return ibuf; }
short IMB_saveiff(struct ImBuf *ibuf, const char *name, int flags) { const ImFileType *type; errno = 0; BLI_assert(!BLI_path_is_rel(name)); if (ibuf == NULL) return (false); ibuf->flags = flags; for (type = IMB_FILE_TYPES; type < IMB_FILE_TYPES_LAST; type++) { if (type->save && type->ftype(type, ibuf)) { ImBuf *write_ibuf; short result = false; write_ibuf = prepare_write_imbuf(type, ibuf); result = type->save(write_ibuf, name, flags); if (write_ibuf != ibuf) IMB_freeImBuf(write_ibuf); return result; } } fprintf(stderr, "Couldn't save picture.\n"); return false; }
int IMB_ispic_type(const char *name) { /* increased from 32 to 64 because of the bitmaps header size */ #define HEADER_SIZE 64 unsigned char buf[HEADER_SIZE]; const ImFileType *type; BLI_stat_t st; int fp; BLI_assert(!BLI_path_is_rel(name)); if (UTIL_DEBUG) printf("%s: loading %s\n", __func__, name); if (BLI_stat(name, &st) == -1) return false; if (((st.st_mode) & S_IFMT) != S_IFREG) return false; if ((fp = BLI_open(name, O_BINARY | O_RDONLY, 0)) == -1) return false; memset(buf, 0, sizeof(buf)); if (read(fp, buf, HEADER_SIZE) <= 0) { close(fp); return false; } close(fp); /* XXX move this exception */ if ((BIG_LONG(((int *)buf)[0]) & 0xfffffff0) == 0xffd8ffe0) return IMB_FTYPE_JPG; for (type = IMB_FILE_TYPES; type < IMB_FILE_TYPES_LAST; type++) { if (type->is_a) { if (type->is_a(buf)) { return type->filetype; } } else if (type->is_a_filepath) { if (type->is_a_filepath(name)) { return type->filetype; } } } return 0; #undef HEADER_SIZE }
int imb_get_anim_type(const char *name) { int type; BLI_stat_t st; BLI_assert(!BLI_path_is_rel(name)); if (UTIL_DEBUG) printf("%s: %s\n", __func__, name); #ifndef _WIN32 # ifdef WITH_QUICKTIME if (isqtime(name)) return (ANIM_QTIME); # endif # ifdef WITH_FFMPEG /* stat test below fails on large files > 4GB */ if (isffmpeg(name)) return (ANIM_FFMPEG); # endif if (BLI_stat(name, &st) == -1) return(0); if (((st.st_mode) & S_IFMT) != S_IFREG) return(0); if (isavi(name)) return (ANIM_AVI); if (ismovie(name)) return (ANIM_MOVIE); #else if (BLI_stat(name, &st) == -1) return(0); if (((st.st_mode) & S_IFMT) != S_IFREG) return(0); if (ismovie(name)) return (ANIM_MOVIE); # ifdef WITH_QUICKTIME if (isqtime(name)) return (ANIM_QTIME); # endif # ifdef WITH_FFMPEG if (isffmpeg(name)) return (ANIM_FFMPEG); # endif if (isavi(name)) return (ANIM_AVI); #endif #ifdef WITH_REDCODE if (isredcode(name)) return (ANIM_REDCODE); #endif type = IMB_ispic(name); if (type) { return ANIM_SEQUENCE; } return ANIM_NONE; }
/** * Returns the st_mode from statting the specified path name, or 0 if it couldn't be statted * (most likely doesn't exist or no access). */ int BLI_exists(const char *name) { #if defined(WIN32) BLI_stat_t st; wchar_t *tmp_16 = alloc_utf16_from_8(name, 1); int len, res; unsigned int old_error_mode; len = wcslen(tmp_16); /* in Windows #stat doesn't recognize dir ending on a slash * so we remove it here */ if (len > 3 && (tmp_16[len - 1] == L'\\' || tmp_16[len - 1] == L'/')) { tmp_16[len - 1] = '\0'; } /* two special cases where the trailing slash is needed: * 1. after the share part of a UNC path * 2. after the C:\ when the path is the volume only */ if ((len >= 3) && (tmp_16[0] == L'\\') && (tmp_16[1] == L'\\')) { BLI_cleanup_unc_16(tmp_16); } if ((tmp_16[1] == L':') && (tmp_16[2] == L'\0')) { tmp_16[2] = L'\\'; tmp_16[3] = L'\0'; } /* change error mode so user does not get a "no disk in drive" popup * when looking for a file on an empty CD/DVD drive */ old_error_mode = SetErrorMode(SEM_FAILCRITICALERRORS | SEM_NOOPENFILEERRORBOX); res = BLI_wstat(tmp_16, &st); SetErrorMode(old_error_mode); free(tmp_16); if (res == -1) return(0); #else struct stat st; BLI_assert(name); BLI_assert(!BLI_path_is_rel(name)); if (stat(name, &st)) return(0); #endif return(st.st_mode); }
void packLibraries(Main *bmain, ReportList *reports) { Library *lib; /* test for relativenss */ for (lib = bmain->library.first; lib; lib = lib->id.next) if (!BLI_path_is_rel(lib->name)) break; if (lib) { BKE_reportf(reports, RPT_ERROR, "Cannot pack absolute file: '%s'", lib->name); return; } for (lib = bmain->library.first; lib; lib = lib->id.next) if (lib->packedfile == NULL) lib->packedfile = newPackedFile(reports, lib->name, bmain->name); }
void BKE_library_filepath_set(Library *lib, const char *filepath) { /* in some cases this is used to update the absolute path from the * relative */ if (lib->name != filepath) { BLI_strncpy(lib->name, filepath, sizeof(lib->name)); } BLI_strncpy(lib->filepath, filepath, sizeof(lib->filepath)); /* not essential but set filepath is an absolute copy of value which * is more useful if its kept in sync */ if (BLI_path_is_rel(lib->filepath)) { /* note that the file may be unsaved, in this case, setting the * filepath on an indirectly linked path is not allowed from the * outliner, and its not really supported but allow from here for now * since making local could cause this to be directly linked - campbell */ const char *basepath = lib->parent ? lib->parent->filepath : G.main->name; BLI_path_abs(lib->filepath, basepath); } }
struct anim *IMB_open_anim(const char *name, int ib_flags, int streamindex, char colorspace[IM_MAX_SPACE]) { struct anim *anim; BLI_assert(!BLI_path_is_rel(name)); anim = (struct anim *)MEM_callocN(sizeof(struct anim), "anim struct"); if (anim != NULL) { if (colorspace) { colorspace_set_default_role(colorspace, IM_MAX_SPACE, COLOR_ROLE_DEFAULT_BYTE); BLI_strncpy(anim->colorspace, colorspace, sizeof(anim->colorspace)); } else { colorspace_set_default_role(anim->colorspace, sizeof(anim->colorspace), COLOR_ROLE_DEFAULT_BYTE); } BLI_strncpy(anim->name, name, sizeof(anim->name)); anim->ib_flags = ib_flags; anim->streamindex = streamindex; } return(anim); }
int BLI_path_abs(char *path, const char *basepath) { int wasrelative = BLI_path_is_rel(path); char tmp[FILE_MAX]; char base[FILE_MAX]; #ifdef WIN32 char vol[3] = {'\0', '\0', '\0'}; BLI_strncpy(vol, path, 3); /* we are checking here if we have an absolute path that is not in the current * blend file as a lib main - we are basically checking for the case that a * UNIX root '/' is passed. */ if (!wasrelative && (vol[1] != ':' && (vol[0] == '\0' || vol[0] == '/' || vol[0] == '\\'))) { char *p = path; get_default_root(tmp); // get rid of the slashes at the beginning of the path while (*p == '\\' || *p == '/') { p++; } strcat(tmp, p); } else { BLI_strncpy(tmp, path, FILE_MAX); } #else BLI_strncpy(tmp, path, sizeof(tmp)); /* Check for loading a windows path on a posix system * in this case, there is no use in trying C:/ since it * will never exist on a unix os. * * Add a / prefix and lowercase the driveletter, remove the : * C:\foo.JPG -> /c/foo.JPG */ if (isalpha(tmp[0]) && tmp[1] == ':' && (tmp[2] == '\\' || tmp[2] == '/') ) { tmp[1] = tolower(tmp[0]); /* replace ':' with driveletter */ tmp[0] = '/'; /* '\' the slash will be converted later */ } #endif BLI_strncpy(base, basepath, sizeof(base)); /* file component is ignored, so don't bother with the trailing slash */ BLI_cleanup_path(NULL, base); /* push slashes into unix mode - strings entering this part are * potentially messed up: having both back- and forward slashes. * Here we push into one conform direction, and at the end we * push them into the system specific dir. This ensures uniformity * of paths and solving some problems (and prevent potential future * ones) -jesterKing. */ BLI_char_switch(tmp, '\\', '/'); BLI_char_switch(base, '\\', '/'); /* Paths starting with // will get the blend file as their base, * this isn't standard in any os but is used in blender all over the place */ if (wasrelative) { char *lslash = BLI_last_slash(base); if (lslash) { int baselen = (int) (lslash - base) + 1; /* use path for temp storage here, we copy back over it right away */ BLI_strncpy(path, tmp + 2, FILE_MAX); memcpy(tmp, base, baselen); BLI_strncpy(tmp + baselen, path, sizeof(tmp) - baselen); BLI_strncpy(path, tmp, FILE_MAX); } else { BLI_strncpy(path, tmp + 2, FILE_MAX); } } else { BLI_strncpy(path, tmp, FILE_MAX); } BLI_cleanup_path(NULL, path); #ifdef WIN32 /* skip first two chars, which in case of * absolute path will be drive:/blabla and * in case of relpath //blabla/. So relpath * // will be retained, rest will be nice and * shiny win32 backward slashes :) -jesterKing */ BLI_char_switch(path + 2, '/', '\\'); #endif return wasrelative; }
void BLI_path_rel(char *file, const char *relfile) { char *lslash; char temp[FILE_MAX]; char res[FILE_MAX]; /* if file is already relative, bail out */ if (BLI_path_is_rel(file)) { return; } /* also bail out if relative path is not set */ if (relfile[0] == '\0') { return; } #ifdef WIN32 if (BLI_strnlen(relfile, 3) > 2 && relfile[1] != ':') { char *ptemp; /* fix missing volume name in relative base, * can happen with old recent-files.txt files */ get_default_root(temp); ptemp = &temp[2]; if (relfile[0] != '\\' && relfile[0] != '/') { ptemp++; } BLI_strncpy(ptemp, relfile, FILE_MAX - 3); } else { BLI_strncpy(temp, relfile, FILE_MAX); } if (BLI_strnlen(file, 3) > 2) { if (temp[1] == ':' && file[1] == ':' && temp[0] != file[0]) return; } #else BLI_strncpy(temp, relfile, FILE_MAX); #endif BLI_char_switch(temp, '\\', '/'); BLI_char_switch(file, '\\', '/'); /* remove /./ which confuse the following slash counting... */ BLI_cleanup_path(NULL, file); BLI_cleanup_path(NULL, temp); /* the last slash in the file indicates where the path part ends */ lslash = BLI_last_slash(temp); if (lslash) { /* find the prefix of the filename that is equal for both filenames. * This is replaced by the two slashes at the beginning */ char *p = temp; char *q = file; #ifdef WIN32 while (tolower(*p) == tolower(*q)) #else while (*p == *q) #endif { p++; q++; /* don't search beyond the end of the string * in the rare case they match */ if ((*p == '\0') || (*q == '\0')) { break; } } /* we might have passed the slash when the beginning of a dir matches * so we rewind. Only check on the actual filename */ if (*q != '/') { while ( (q >= file) && (*q != '/') ) { --q; --p; } } else if (*p != '/') { while ( (p >= temp) && (*p != '/') ) { --p; --q; } } strcpy(res, "//"); /* p now points to the slash that is at the beginning of the part * where the path is different from the relative path. * We count the number of directories we need to go up in the * hierarchy to arrive at the common 'prefix' of the path */ while (p && p < lslash) { if (*p == '/') strcat(res, "../"); p++; } strcat(res, q + 1); /* don't copy the slash at the beginning */ #ifdef WIN32 BLI_char_switch(res + 2, '/', '\\'); #endif strcpy(file, res); } }