forked from Mirrors/freeswitch
0488a5109a
git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@3733 d0543943-73ff-0310-b7d9-9358b9ac24b2
756 lines
18 KiB
C
756 lines
18 KiB
C
/* Licensed to the Apache Software Foundation (ASF) under one or more
|
|
* contributor license agreements. See the NOTICE file distributed with
|
|
* this work for additional information regarding copyright ownership.
|
|
* The ASF licenses this file to You under the Apache License, Version 2.0
|
|
* (the "License"); you may not use this file except in compliance with
|
|
* the License. You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
#include <stdio.h>
|
|
#include <process.h>
|
|
#include <string.h>
|
|
#include <stdlib.h>
|
|
#include <sys/types.h>
|
|
#include <dirent.h>
|
|
|
|
typedef char bool;
|
|
#define false 0
|
|
#define true (!false)
|
|
|
|
bool silent = false;
|
|
bool shared = false;
|
|
bool export_all = false;
|
|
enum mode_t { mCompile, mLink, mInstall };
|
|
enum output_type_t { otGeneral, otObject, otProgram, otStaticLibrary, otDynamicLibrary };
|
|
|
|
#ifdef __EMX__
|
|
# define SHELL_CMD "sh"
|
|
# define CC "gcc"
|
|
# define GEN_EXPORTS "emxexp"
|
|
# define DEF2IMPLIB_CMD "emximp"
|
|
# define SHARE_SW "-Zdll -Zmtd"
|
|
# define USE_OMF true
|
|
# define TRUNCATE_DLL_NAME
|
|
# define DYNAMIC_LIB_EXT "dll"
|
|
# define EXE_EXT ".exe"
|
|
|
|
# if USE_OMF
|
|
/* OMF is the native format under OS/2 */
|
|
# define STATIC_LIB_EXT "lib"
|
|
# define OBJECT_EXT "obj"
|
|
# define LIBRARIAN "emxomfar"
|
|
# else
|
|
/* but the alternative, a.out, can fork() which is sometimes necessary */
|
|
# define STATIC_LIB_EXT "a"
|
|
# define OBJECT_EXT "o"
|
|
# define LIBRARIAN "ar"
|
|
# endif
|
|
#endif
|
|
|
|
|
|
typedef struct {
|
|
char *arglist[1024];
|
|
int num_args;
|
|
enum mode_t mode;
|
|
enum output_type_t output_type;
|
|
char *output_name;
|
|
char *stub_name;
|
|
char *tmp_dirs[1024];
|
|
int num_tmp_dirs;
|
|
char *obj_files[1024];
|
|
int num_obj_files;
|
|
} cmd_data_t;
|
|
|
|
void parse_args(int argc, char *argv[], cmd_data_t *cmd_data);
|
|
bool parse_long_opt(char *arg, cmd_data_t *cmd_data);
|
|
int parse_short_opt(char *arg, cmd_data_t *cmd_data);
|
|
bool parse_input_file_name(char *arg, cmd_data_t *cmd_data);
|
|
bool parse_output_file_name(char *arg, cmd_data_t *cmd_data);
|
|
void post_parse_fixup(cmd_data_t *cmd_data);
|
|
bool explode_static_lib(char *lib, cmd_data_t *cmd_data);
|
|
int execute_command(cmd_data_t *cmd_data);
|
|
char *shell_esc(const char *str);
|
|
void cleanup_tmp_dirs(cmd_data_t *cmd_data);
|
|
void generate_def_file(cmd_data_t *cmd_data);
|
|
char *nameof(char *fullpath);
|
|
char *truncate_dll_name(char *path);
|
|
|
|
|
|
int main(int argc, char *argv[])
|
|
{
|
|
int rc;
|
|
cmd_data_t cmd_data;
|
|
|
|
memset(&cmd_data, 0, sizeof(cmd_data));
|
|
cmd_data.mode = mCompile;
|
|
cmd_data.output_type = otGeneral;
|
|
|
|
parse_args(argc, argv, &cmd_data);
|
|
rc = execute_command(&cmd_data);
|
|
|
|
if (rc == 0 && cmd_data.stub_name) {
|
|
fopen(cmd_data.stub_name, "w");
|
|
}
|
|
|
|
cleanup_tmp_dirs(&cmd_data);
|
|
return rc;
|
|
}
|
|
|
|
|
|
|
|
void parse_args(int argc, char *argv[], cmd_data_t *cmd_data)
|
|
{
|
|
int a;
|
|
char *arg;
|
|
bool argused;
|
|
|
|
for (a=1; a < argc; a++) {
|
|
arg = argv[a];
|
|
argused = false;
|
|
|
|
if (arg[0] == '-') {
|
|
if (arg[1] == '-') {
|
|
argused = parse_long_opt(arg + 2, cmd_data);
|
|
} else if (arg[1] == 'o' && a+1 < argc) {
|
|
cmd_data->arglist[cmd_data->num_args++] = arg;
|
|
arg = argv[++a];
|
|
argused = parse_output_file_name(arg, cmd_data);
|
|
} else {
|
|
int num_used = parse_short_opt(arg + 1, cmd_data);
|
|
argused = num_used > 0;
|
|
|
|
if (num_used > 1) {
|
|
a += num_used - 1;
|
|
}
|
|
}
|
|
} else {
|
|
argused = parse_input_file_name(arg, cmd_data);
|
|
}
|
|
|
|
if (!argused) {
|
|
cmd_data->arglist[cmd_data->num_args++] = arg;
|
|
}
|
|
}
|
|
|
|
post_parse_fixup(cmd_data);
|
|
}
|
|
|
|
|
|
|
|
bool parse_long_opt(char *arg, cmd_data_t *cmd_data)
|
|
{
|
|
char *equal_pos = strchr(arg, '=');
|
|
char var[50];
|
|
char value[500];
|
|
|
|
if (equal_pos) {
|
|
strncpy(var, arg, equal_pos - arg);
|
|
var[equal_pos - arg] = 0;
|
|
strcpy(value, equal_pos + 1);
|
|
} else {
|
|
strcpy(var, arg);
|
|
}
|
|
|
|
if (strcmp(var, "silent") == 0) {
|
|
silent = true;
|
|
} else if (strcmp(var, "mode") == 0) {
|
|
if (strcmp(value, "compile") == 0) {
|
|
cmd_data->mode = mCompile;
|
|
cmd_data->output_type = otObject;
|
|
}
|
|
|
|
if (strcmp(value, "link") == 0) {
|
|
cmd_data->mode = mLink;
|
|
}
|
|
|
|
if (strcmp(value, "install") == 0) {
|
|
cmd_data->mode = mInstall;
|
|
}
|
|
} else if (strcmp(var, "shared") == 0) {
|
|
shared = true;
|
|
} else if (strcmp(var, "export-all") == 0) {
|
|
export_all = true;
|
|
} else {
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
|
|
|
|
int parse_short_opt(char *arg, cmd_data_t *cmd_data)
|
|
{
|
|
if (strcmp(arg, "export-dynamic") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
if (strcmp(arg, "module") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
if (strcmp(arg, "Zexe") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
if (strcmp(arg, "avoid-version") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
if (strcmp(arg, "prefer-pic") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
if (strcmp(arg, "prefer-non-pic") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
if (strcmp(arg, "version-info") == 0 ) {
|
|
return 2;
|
|
}
|
|
|
|
if (strcmp(arg, "no-install") == 0) {
|
|
return 1;
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
|
|
|
|
bool parse_input_file_name(char *arg, cmd_data_t *cmd_data)
|
|
{
|
|
char *ext = strrchr(arg, '.');
|
|
char *name = strrchr(arg, '/');
|
|
int pathlen;
|
|
char *newarg;
|
|
|
|
if (!ext) {
|
|
return false;
|
|
}
|
|
|
|
ext++;
|
|
|
|
if (name == NULL) {
|
|
name = strrchr(arg, '\\');
|
|
|
|
if (name == NULL) {
|
|
name = arg;
|
|
} else {
|
|
name++;
|
|
}
|
|
} else {
|
|
name++;
|
|
}
|
|
|
|
pathlen = name - arg;
|
|
|
|
if (strcmp(ext, "lo") == 0) {
|
|
newarg = (char *)malloc(strlen(arg) + 10);
|
|
strcpy(newarg, arg);
|
|
strcpy(newarg + (ext - arg), OBJECT_EXT);
|
|
cmd_data->arglist[cmd_data->num_args++] = newarg;
|
|
cmd_data->obj_files[cmd_data->num_obj_files++] = newarg;
|
|
return true;
|
|
}
|
|
|
|
if (strcmp(ext, "la") == 0) {
|
|
newarg = (char *)malloc(strlen(arg) + 10);
|
|
strcpy(newarg, arg);
|
|
newarg[pathlen] = 0;
|
|
strcat(newarg, ".libs/");
|
|
|
|
if (strncmp(name, "lib", 3) == 0) {
|
|
name += 3;
|
|
}
|
|
|
|
strcat(newarg, name);
|
|
ext = strrchr(newarg, '.') + 1;
|
|
|
|
if (shared && cmd_data->mode == mInstall) {
|
|
strcpy(ext, DYNAMIC_LIB_EXT);
|
|
newarg = truncate_dll_name(newarg);
|
|
} else {
|
|
strcpy(ext, STATIC_LIB_EXT);
|
|
}
|
|
|
|
cmd_data->arglist[cmd_data->num_args++] = newarg;
|
|
return true;
|
|
}
|
|
|
|
if (strcmp(ext, "c") == 0) {
|
|
if (cmd_data->stub_name == NULL) {
|
|
cmd_data->stub_name = (char *)malloc(strlen(arg) + 4);
|
|
strcpy(cmd_data->stub_name, arg);
|
|
strcpy(strrchr(cmd_data->stub_name, '.') + 1, "lo");
|
|
}
|
|
}
|
|
|
|
if (strcmp(name, CC) == 0 || strcmp(name, CC EXE_EXT) == 0) {
|
|
if (cmd_data->output_type == otGeneral) {
|
|
cmd_data->output_type = otObject;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
|
|
|
|
bool parse_output_file_name(char *arg, cmd_data_t *cmd_data)
|
|
{
|
|
char *name = strrchr(arg, '/');
|
|
char *ext = strrchr(arg, '.');
|
|
char *newarg = NULL, *newext;
|
|
int pathlen;
|
|
|
|
if (name == NULL) {
|
|
name = strrchr(arg, '\\');
|
|
|
|
if (name == NULL) {
|
|
name = arg;
|
|
} else {
|
|
name++;
|
|
}
|
|
} else {
|
|
name++;
|
|
}
|
|
|
|
if (!ext) {
|
|
cmd_data->stub_name = arg;
|
|
cmd_data->output_type = otProgram;
|
|
newarg = (char *)malloc(strlen(arg) + 5);
|
|
strcpy(newarg, arg);
|
|
strcat(newarg, EXE_EXT);
|
|
cmd_data->arglist[cmd_data->num_args++] = newarg;
|
|
cmd_data->output_name = newarg;
|
|
return true;
|
|
}
|
|
|
|
ext++;
|
|
pathlen = name - arg;
|
|
|
|
if (strcmp(ext, "la") == 0) {
|
|
cmd_data->stub_name = arg;
|
|
cmd_data->output_type = shared ? otDynamicLibrary : otStaticLibrary;
|
|
newarg = (char *)malloc(strlen(arg) + 10);
|
|
mkdir(".libs", 0);
|
|
strcpy(newarg, ".libs/");
|
|
|
|
if (strncmp(arg, "lib", 3) == 0) {
|
|
arg += 3;
|
|
}
|
|
|
|
strcat(newarg, arg);
|
|
newext = strrchr(newarg, '.') + 1;
|
|
strcpy(newext, shared ? DYNAMIC_LIB_EXT : STATIC_LIB_EXT);
|
|
|
|
#ifdef TRUNCATE_DLL_NAME
|
|
if (shared) {
|
|
newarg = truncate_dll_name(newarg);
|
|
}
|
|
#endif
|
|
|
|
cmd_data->arglist[cmd_data->num_args++] = newarg;
|
|
cmd_data->output_name = newarg;
|
|
return true;
|
|
}
|
|
|
|
if (strcmp(ext, "lo") == 0) {
|
|
cmd_data->stub_name = arg;
|
|
cmd_data->output_type = otObject;
|
|
newarg = (char *)malloc(strlen(arg) + 2);
|
|
strcpy(newarg, arg);
|
|
ext = strrchr(newarg, '.') + 1;
|
|
strcpy(ext, OBJECT_EXT);
|
|
cmd_data->arglist[cmd_data->num_args++] = newarg;
|
|
cmd_data->output_name = newarg;
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
|
|
|
|
void post_parse_fixup(cmd_data_t *cmd_data)
|
|
{
|
|
int a;
|
|
char *arg;
|
|
char *ext;
|
|
|
|
if (cmd_data->output_type == otStaticLibrary && cmd_data->mode == mLink) {
|
|
/* We do a real hatchet job on the args when making a static library
|
|
* removing all compiler switches & any other cruft that ar won't like
|
|
* We also need to explode any libraries listed
|
|
*/
|
|
|
|
for (a=0; a < cmd_data->num_args; a++) {
|
|
arg = cmd_data->arglist[a];
|
|
|
|
if (arg) {
|
|
ext = strrchr(arg, '.');
|
|
|
|
if (ext) {
|
|
ext++;
|
|
}
|
|
|
|
if (arg[0] == '-') {
|
|
cmd_data->arglist[a] = NULL;
|
|
|
|
if (strcmp(arg, "-rpath") == 0 && a+1 < cmd_data->num_args) {
|
|
cmd_data->arglist[a+1] = NULL;
|
|
}
|
|
|
|
if (strcmp(arg, "-R") == 0 && a+1 < cmd_data->num_args) {
|
|
cmd_data->arglist[a+1] = NULL;
|
|
}
|
|
|
|
if (strcmp(arg, "-version-info") == 0 && a+1 < cmd_data->num_args) {
|
|
cmd_data->arglist[a+1] = NULL;
|
|
}
|
|
|
|
if (strcmp(arg, "-Zstack") == 0 && a+1 < cmd_data->num_args) {
|
|
cmd_data->arglist[a+1] = NULL;
|
|
}
|
|
|
|
if (strcmp(arg, "-o") == 0) {
|
|
a++;
|
|
}
|
|
}
|
|
|
|
if (strcmp(arg, CC) == 0 || strcmp(arg, CC EXE_EXT) == 0) {
|
|
cmd_data->arglist[a] = LIBRARIAN " cr";
|
|
}
|
|
|
|
if (ext) {
|
|
if (strcmp(ext, "h") == 0 || strcmp(ext, "c") == 0) {
|
|
/* ignore source files, they don't belong in a library */
|
|
cmd_data->arglist[a] = NULL;
|
|
}
|
|
|
|
if (strcmp(ext, STATIC_LIB_EXT) == 0) {
|
|
cmd_data->arglist[a] = NULL;
|
|
explode_static_lib(arg, cmd_data);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (cmd_data->output_type == otDynamicLibrary) {
|
|
for (a=0; a < cmd_data->num_args; a++) {
|
|
arg = cmd_data->arglist[a];
|
|
|
|
if (arg) {
|
|
if (strcmp(arg, "-rpath") == 0 && a+1 < cmd_data->num_args) {
|
|
cmd_data->arglist[a] = NULL;
|
|
cmd_data->arglist[a+1] = NULL;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (export_all) {
|
|
generate_def_file(cmd_data);
|
|
}
|
|
}
|
|
|
|
#if USE_OMF
|
|
if (cmd_data->output_type == otObject ||
|
|
cmd_data->output_type == otProgram ||
|
|
cmd_data->output_type == otDynamicLibrary) {
|
|
cmd_data->arglist[cmd_data->num_args++] = "-Zomf";
|
|
}
|
|
#endif
|
|
|
|
if (shared && (cmd_data->output_type == otObject || cmd_data->output_type == otDynamicLibrary)) {
|
|
cmd_data->arglist[cmd_data->num_args++] = SHARE_SW;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
int execute_command(cmd_data_t *cmd_data)
|
|
{
|
|
int target = 0;
|
|
char *command;
|
|
int a, total_len = 0;
|
|
char *args[4];
|
|
|
|
for (a=0; a < cmd_data->num_args; a++) {
|
|
if (cmd_data->arglist[a]) {
|
|
total_len += strlen(cmd_data->arglist[a]) + 1;
|
|
}
|
|
}
|
|
|
|
command = (char *)malloc( total_len );
|
|
command[0] = 0;
|
|
|
|
for (a=0; a < cmd_data->num_args; a++) {
|
|
if (cmd_data->arglist[a]) {
|
|
strcat(command, cmd_data->arglist[a]);
|
|
strcat(command, " ");
|
|
}
|
|
}
|
|
|
|
command[strlen(command)-1] = 0;
|
|
|
|
if (!silent) {
|
|
puts(command);
|
|
}
|
|
|
|
cmd_data->num_args = target;
|
|
cmd_data->arglist[cmd_data->num_args] = NULL;
|
|
command = shell_esc(command);
|
|
|
|
args[0] = SHELL_CMD;
|
|
args[1] = "-c";
|
|
args[2] = command;
|
|
args[3] = NULL;
|
|
return spawnvp(P_WAIT, args[0], args);
|
|
}
|
|
|
|
|
|
|
|
char *shell_esc(const char *str)
|
|
{
|
|
char *cmd;
|
|
unsigned char *d;
|
|
const unsigned char *s;
|
|
|
|
cmd = (char *)malloc(2 * strlen(str) + 1);
|
|
d = (unsigned char *)cmd;
|
|
s = (const unsigned char *)str;
|
|
|
|
for (; *s; ++s) {
|
|
if (*s == '"' || *s == '\\') {
|
|
*d++ = '\\';
|
|
}
|
|
*d++ = *s;
|
|
}
|
|
|
|
*d = '\0';
|
|
return cmd;
|
|
}
|
|
|
|
|
|
|
|
bool explode_static_lib(char *lib, cmd_data_t *cmd_data)
|
|
{
|
|
char tmpdir[1024];
|
|
char savewd[1024];
|
|
char cmd[1024];
|
|
char *name;
|
|
DIR *dir;
|
|
struct dirent *entry;
|
|
|
|
strcpy(tmpdir, lib);
|
|
strcat(tmpdir, ".exploded");
|
|
|
|
mkdir(tmpdir, 0);
|
|
cmd_data->tmp_dirs[cmd_data->num_tmp_dirs++] = strdup(tmpdir);
|
|
getcwd(savewd, sizeof(savewd));
|
|
|
|
if (chdir(tmpdir) != 0)
|
|
return false;
|
|
|
|
strcpy(cmd, LIBRARIAN " x ");
|
|
name = strrchr(lib, '/');
|
|
|
|
if (name) {
|
|
name++;
|
|
} else {
|
|
name = lib;
|
|
}
|
|
|
|
strcat(cmd, "../");
|
|
strcat(cmd, name);
|
|
system(cmd);
|
|
chdir(savewd);
|
|
dir = opendir(tmpdir);
|
|
|
|
while ((entry = readdir(dir)) != NULL) {
|
|
if (entry->d_name[0] != '.') {
|
|
strcpy(cmd, tmpdir);
|
|
strcat(cmd, "/");
|
|
strcat(cmd, entry->d_name);
|
|
cmd_data->arglist[cmd_data->num_args++] = strdup(cmd);
|
|
}
|
|
}
|
|
|
|
closedir(dir);
|
|
return true;
|
|
}
|
|
|
|
|
|
|
|
void cleanup_tmp_dir(char *dirname)
|
|
{
|
|
DIR *dir;
|
|
struct dirent *entry;
|
|
char fullname[1024];
|
|
|
|
dir = opendir(dirname);
|
|
|
|
if (dir == NULL)
|
|
return;
|
|
|
|
while ((entry = readdir(dir)) != NULL) {
|
|
if (entry->d_name[0] != '.') {
|
|
strcpy(fullname, dirname);
|
|
strcat(fullname, "/");
|
|
strcat(fullname, entry->d_name);
|
|
remove(fullname);
|
|
}
|
|
}
|
|
|
|
rmdir(dirname);
|
|
}
|
|
|
|
|
|
|
|
void cleanup_tmp_dirs(cmd_data_t *cmd_data)
|
|
{
|
|
int d;
|
|
|
|
for (d=0; d < cmd_data->num_tmp_dirs; d++) {
|
|
cleanup_tmp_dir(cmd_data->tmp_dirs[d]);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
void generate_def_file(cmd_data_t *cmd_data)
|
|
{
|
|
char def_file[1024];
|
|
char implib_file[1024];
|
|
char *ext;
|
|
FILE *hDef;
|
|
char *export_args[1024];
|
|
int num_export_args = 0;
|
|
char *cmd;
|
|
int cmd_size = 0;
|
|
int a;
|
|
|
|
if (cmd_data->output_name) {
|
|
strcpy(def_file, cmd_data->output_name);
|
|
strcat(def_file, ".def");
|
|
hDef = fopen(def_file, "w");
|
|
|
|
if (hDef != NULL) {
|
|
fprintf(hDef, "LIBRARY '%s' INITINSTANCE\n", nameof(cmd_data->output_name));
|
|
fprintf(hDef, "DATA NONSHARED\n");
|
|
fprintf(hDef, "EXPORTS\n");
|
|
fclose(hDef);
|
|
|
|
for (a=0; a < cmd_data->num_obj_files; a++) {
|
|
cmd_size += strlen(cmd_data->obj_files[a]) + 1;
|
|
}
|
|
|
|
cmd_size += strlen(GEN_EXPORTS) + strlen(def_file) + 3;
|
|
cmd = (char *)malloc(cmd_size);
|
|
strcpy(cmd, GEN_EXPORTS);
|
|
|
|
for (a=0; a < cmd_data->num_obj_files; a++) {
|
|
strcat(cmd, " ");
|
|
strcat(cmd, cmd_data->obj_files[a] );
|
|
}
|
|
|
|
strcat(cmd, ">>");
|
|
strcat(cmd, def_file);
|
|
puts(cmd);
|
|
export_args[num_export_args++] = SHELL_CMD;
|
|
export_args[num_export_args++] = "-c";
|
|
export_args[num_export_args++] = cmd;
|
|
export_args[num_export_args++] = NULL;
|
|
spawnvp(P_WAIT, export_args[0], export_args);
|
|
cmd_data->arglist[cmd_data->num_args++] = strdup(def_file);
|
|
|
|
/* Now make an import library for the dll */
|
|
num_export_args = 0;
|
|
export_args[num_export_args++] = DEF2IMPLIB_CMD;
|
|
export_args[num_export_args++] = "-o";
|
|
|
|
strcpy(implib_file, ".libs/");
|
|
strcat(implib_file, cmd_data->stub_name);
|
|
ext = strrchr(implib_file, '.');
|
|
|
|
if (ext)
|
|
*ext = 0;
|
|
|
|
strcat(implib_file, ".");
|
|
strcat(implib_file, STATIC_LIB_EXT);
|
|
|
|
export_args[num_export_args++] = implib_file;
|
|
export_args[num_export_args++] = def_file;
|
|
export_args[num_export_args++] = NULL;
|
|
spawnvp(P_WAIT, export_args[0], export_args);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|
|
/* returns just a file's name without path or extension */
|
|
char *nameof(char *fullpath)
|
|
{
|
|
char buffer[1024];
|
|
char *ext;
|
|
char *name = strrchr(fullpath, '/');
|
|
|
|
if (name == NULL) {
|
|
name = strrchr(fullpath, '\\');
|
|
}
|
|
|
|
if (name == NULL) {
|
|
name = fullpath;
|
|
} else {
|
|
name++;
|
|
}
|
|
|
|
strcpy(buffer, name);
|
|
ext = strrchr(buffer, '.');
|
|
|
|
if (ext) {
|
|
*ext = 0;
|
|
return strdup(buffer);
|
|
}
|
|
|
|
return name;
|
|
}
|
|
|
|
|
|
|
|
char *truncate_dll_name(char *path)
|
|
{
|
|
/* Cut DLL name down to 8 characters after removing any mod_ prefix */
|
|
char *tmppath = strdup(path);
|
|
char *newname = strrchr(tmppath, '/') + 1;
|
|
char *ext = strrchr(tmppath, '.');
|
|
int len;
|
|
|
|
if (ext == NULL)
|
|
return tmppath;
|
|
|
|
len = ext - newname;
|
|
|
|
if (strncmp(newname, "mod_", 4) == 0) {
|
|
strcpy(newname, newname + 4);
|
|
len -= 4;
|
|
}
|
|
|
|
if (len > 8) {
|
|
strcpy(newname + 8, strchr(newname, '.'));
|
|
}
|
|
|
|
return tmppath;
|
|
}
|