提交 046ddcd1 编写于 作者: L libb

add gcc01

Change-Id: Ic95c90c55eb5265b733ebe3bf7579bacb831f846
上级 4e784c40
// !$*UTF8*$!
{
archiveVersion = 1;
classes = {
};
objectVersion = 50;
objects = {
/* Begin PBXBuildFile section */
0429423E21BE3BE200D3BF15 /* dso-dlfcn.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429422721BE3BE100D3BF15 /* dso-dlfcn.c */; };
0429423F21BE3BE200D3BF15 /* jsvc-unix.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429422B21BE3BE100D3BF15 /* jsvc-unix.c */; };
0429424021BE3BE200D3BF15 /* arguments.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429422C21BE3BE100D3BF15 /* arguments.c */; };
0429424121BE3BE200D3BF15 /* location.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429422D21BE3BE100D3BF15 /* location.c */; };
0429424221BE3BE200D3BF15 /* debug.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429422F21BE3BE100D3BF15 /* debug.c */; };
0429424321BE3BE200D3BF15 /* signals.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429423021BE3BE100D3BF15 /* signals.c */; };
0429424421BE3BE200D3BF15 /* replace.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429423121BE3BE100D3BF15 /* replace.c */; };
0429424521BE3BE200D3BF15 /* help.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429423721BE3BE200D3BF15 /* help.c */; };
0429424621BE3BE200D3BF15 /* java.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429423821BE3BE200D3BF15 /* java.c */; };
0429424721BE3BE200D3BF15 /* locks.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429423A21BE3BE200D3BF15 /* locks.c */; };
0429424821BE3BE200D3BF15 /* home.c in Sources */ = {isa = PBXBuildFile; fileRef = 0429423B21BE3BE200D3BF15 /* home.c */; };
/* End PBXBuildFile section */
/* Begin PBXCopyFilesBuildPhase section */
04C545F221BE2AEB00EF280D /* CopyFiles */ = {
isa = PBXCopyFilesBuildPhase;
buildActionMask = 2147483647;
dstPath = /usr/share/man/man1/;
dstSubfolderSpec = 0;
files = (
);
runOnlyForDeploymentPostprocessing = 1;
};
/* End PBXCopyFilesBuildPhase section */
/* Begin PBXFileReference section */
0429422721BE3BE100D3BF15 /* dso-dlfcn.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = "dso-dlfcn.c"; sourceTree = "<group>"; };
0429422821BE3BE100D3BF15 /* java.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = java.h; sourceTree = "<group>"; };
0429422921BE3BE100D3BF15 /* location.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = location.h; sourceTree = "<group>"; };
0429422A21BE3BE100D3BF15 /* signals.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = signals.h; sourceTree = "<group>"; };
0429422B21BE3BE100D3BF15 /* jsvc-unix.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = "jsvc-unix.c"; sourceTree = "<group>"; };
0429422C21BE3BE100D3BF15 /* arguments.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = arguments.c; sourceTree = "<group>"; };
0429422D21BE3BE100D3BF15 /* location.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = location.c; sourceTree = "<group>"; };
0429422E21BE3BE100D3BF15 /* dso.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = dso.h; sourceTree = "<group>"; };
0429422F21BE3BE100D3BF15 /* debug.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = debug.c; sourceTree = "<group>"; };
0429423021BE3BE100D3BF15 /* signals.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = signals.c; sourceTree = "<group>"; };
0429423121BE3BE100D3BF15 /* replace.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = replace.c; sourceTree = "<group>"; };
0429423221BE3BE100D3BF15 /* debug.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = debug.h; sourceTree = "<group>"; };
0429423321BE3BE100D3BF15 /* version.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = version.h; sourceTree = "<group>"; };
0429423421BE3BE100D3BF15 /* replace.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = replace.h; sourceTree = "<group>"; };
0429423521BE3BE200D3BF15 /* locks.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = locks.h; sourceTree = "<group>"; };
0429423621BE3BE200D3BF15 /* jsvc.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = jsvc.h; sourceTree = "<group>"; };
0429423721BE3BE200D3BF15 /* help.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = help.c; sourceTree = "<group>"; };
0429423821BE3BE200D3BF15 /* java.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = java.c; sourceTree = "<group>"; };
0429423921BE3BE200D3BF15 /* home.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = home.h; sourceTree = "<group>"; };
0429423A21BE3BE200D3BF15 /* locks.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = locks.c; sourceTree = "<group>"; };
0429423B21BE3BE200D3BF15 /* home.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = home.c; sourceTree = "<group>"; };
0429423C21BE3BE200D3BF15 /* help.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = help.h; sourceTree = "<group>"; };
0429423D21BE3BE200D3BF15 /* arguments.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = arguments.h; sourceTree = "<group>"; };
04C545F421BE2AEB00EF280D /* gcc01 */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = gcc01; sourceTree = BUILT_PRODUCTS_DIR; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
04C545F121BE2AEB00EF280D /* Frameworks */ = {
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
);
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */
04C545EB21BE2AEB00EF280D = {
isa = PBXGroup;
children = (
04C545F621BE2AEB00EF280D /* gcc01 */,
04C545F521BE2AEB00EF280D /* Products */,
);
sourceTree = "<group>";
};
04C545F521BE2AEB00EF280D /* Products */ = {
isa = PBXGroup;
children = (
04C545F421BE2AEB00EF280D /* gcc01 */,
);
name = Products;
sourceTree = "<group>";
};
04C545F621BE2AEB00EF280D /* gcc01 */ = {
isa = PBXGroup;
children = (
0429422C21BE3BE100D3BF15 /* arguments.c */,
0429423D21BE3BE200D3BF15 /* arguments.h */,
0429422F21BE3BE100D3BF15 /* debug.c */,
0429423221BE3BE100D3BF15 /* debug.h */,
0429422721BE3BE100D3BF15 /* dso-dlfcn.c */,
0429422E21BE3BE100D3BF15 /* dso.h */,
0429423721BE3BE200D3BF15 /* help.c */,
0429423C21BE3BE200D3BF15 /* help.h */,
0429423B21BE3BE200D3BF15 /* home.c */,
0429423921BE3BE200D3BF15 /* home.h */,
0429423821BE3BE200D3BF15 /* java.c */,
0429422821BE3BE100D3BF15 /* java.h */,
0429422B21BE3BE100D3BF15 /* jsvc-unix.c */,
0429423621BE3BE200D3BF15 /* jsvc.h */,
0429422D21BE3BE100D3BF15 /* location.c */,
0429422921BE3BE100D3BF15 /* location.h */,
0429423A21BE3BE200D3BF15 /* locks.c */,
0429423521BE3BE200D3BF15 /* locks.h */,
0429423121BE3BE100D3BF15 /* replace.c */,
0429423421BE3BE100D3BF15 /* replace.h */,
0429423021BE3BE100D3BF15 /* signals.c */,
0429422A21BE3BE100D3BF15 /* signals.h */,
0429423321BE3BE100D3BF15 /* version.h */,
);
path = gcc01;
sourceTree = "<group>";
};
/* End PBXGroup section */
/* Begin PBXNativeTarget section */
04C545F321BE2AEB00EF280D /* gcc01 */ = {
isa = PBXNativeTarget;
buildConfigurationList = 04C545FB21BE2AEB00EF280D /* Build configuration list for PBXNativeTarget "gcc01" */;
buildPhases = (
04C545F021BE2AEB00EF280D /* Sources */,
04C545F121BE2AEB00EF280D /* Frameworks */,
04C545F221BE2AEB00EF280D /* CopyFiles */,
);
buildRules = (
);
dependencies = (
);
name = gcc01;
productName = gcc01;
productReference = 04C545F421BE2AEB00EF280D /* gcc01 */;
productType = "com.apple.product-type.tool";
};
/* End PBXNativeTarget section */
/* Begin PBXProject section */
04C545EC21BE2AEB00EF280D /* Project object */ = {
isa = PBXProject;
attributes = {
LastUpgradeCheck = 0930;
ORGANIZATIONNAME = BaiRuiTechnology;
TargetAttributes = {
04C545F321BE2AEB00EF280D = {
CreatedOnToolsVersion = 9.3;
};
};
};
buildConfigurationList = 04C545EF21BE2AEB00EF280D /* Build configuration list for PBXProject "gcc01" */;
compatibilityVersion = "Xcode 9.3";
developmentRegion = en;
hasScannedForEncodings = 0;
knownRegions = (
en,
);
mainGroup = 04C545EB21BE2AEB00EF280D;
productRefGroup = 04C545F521BE2AEB00EF280D /* Products */;
projectDirPath = "";
projectRoot = "";
targets = (
04C545F321BE2AEB00EF280D /* gcc01 */,
);
};
/* End PBXProject section */
/* Begin PBXSourcesBuildPhase section */
04C545F021BE2AEB00EF280D /* Sources */ = {
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
0429424721BE3BE200D3BF15 /* locks.c in Sources */,
0429424521BE3BE200D3BF15 /* help.c in Sources */,
0429424821BE3BE200D3BF15 /* home.c in Sources */,
0429424621BE3BE200D3BF15 /* java.c in Sources */,
0429424121BE3BE200D3BF15 /* location.c in Sources */,
0429424321BE3BE200D3BF15 /* signals.c in Sources */,
0429424221BE3BE200D3BF15 /* debug.c in Sources */,
0429423E21BE3BE200D3BF15 /* dso-dlfcn.c in Sources */,
0429423F21BE3BE200D3BF15 /* jsvc-unix.c in Sources */,
0429424421BE3BE200D3BF15 /* replace.c in Sources */,
0429424021BE3BE200D3BF15 /* arguments.c in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXSourcesBuildPhase section */
/* Begin XCBuildConfiguration section */
04C545F921BE2AEB00EF280D /* Debug */ = {
isa = XCBuildConfiguration;
buildSettings = {
ALWAYS_SEARCH_USER_PATHS = NO;
CLANG_ANALYZER_NONNULL = YES;
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
CLANG_CXX_LIBRARY = "libc++";
CLANG_ENABLE_MODULES = YES;
CLANG_ENABLE_OBJC_ARC = YES;
CLANG_ENABLE_OBJC_WEAK = YES;
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
CLANG_WARN_BOOL_CONVERSION = YES;
CLANG_WARN_COMMA = YES;
CLANG_WARN_CONSTANT_CONVERSION = YES;
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
CLANG_WARN_EMPTY_BODY = YES;
CLANG_WARN_ENUM_CONVERSION = YES;
CLANG_WARN_INFINITE_RECURSION = YES;
CLANG_WARN_INT_CONVERSION = YES;
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
CLANG_WARN_STRICT_PROTOTYPES = YES;
CLANG_WARN_SUSPICIOUS_MOVE = YES;
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
CLANG_WARN_UNREACHABLE_CODE = YES;
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "Mac Developer";
COPY_PHASE_STRIP = NO;
DEBUG_INFORMATION_FORMAT = dwarf;
ENABLE_STRICT_OBJC_MSGSEND = YES;
ENABLE_TESTABILITY = YES;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_DYNAMIC_NO_PIC = NO;
GCC_NO_COMMON_BLOCKS = YES;
GCC_OPTIMIZATION_LEVEL = 0;
GCC_PREPROCESSOR_DEFINITIONS = (
"DEBUG=1",
"$(inherited)",
);
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
GCC_WARN_UNDECLARED_SELECTOR = YES;
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
MACOSX_DEPLOYMENT_TARGET = 10.13;
MTL_ENABLE_DEBUG_INFO = YES;
ONLY_ACTIVE_ARCH = YES;
SDKROOT = macosx;
};
name = Debug;
};
04C545FA21BE2AEB00EF280D /* Release */ = {
isa = XCBuildConfiguration;
buildSettings = {
ALWAYS_SEARCH_USER_PATHS = NO;
CLANG_ANALYZER_NONNULL = YES;
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
CLANG_CXX_LIBRARY = "libc++";
CLANG_ENABLE_MODULES = YES;
CLANG_ENABLE_OBJC_ARC = YES;
CLANG_ENABLE_OBJC_WEAK = YES;
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
CLANG_WARN_BOOL_CONVERSION = YES;
CLANG_WARN_COMMA = YES;
CLANG_WARN_CONSTANT_CONVERSION = YES;
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
CLANG_WARN_EMPTY_BODY = YES;
CLANG_WARN_ENUM_CONVERSION = YES;
CLANG_WARN_INFINITE_RECURSION = YES;
CLANG_WARN_INT_CONVERSION = YES;
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
CLANG_WARN_STRICT_PROTOTYPES = YES;
CLANG_WARN_SUSPICIOUS_MOVE = YES;
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
CLANG_WARN_UNREACHABLE_CODE = YES;
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
CODE_SIGN_IDENTITY = "Mac Developer";
COPY_PHASE_STRIP = NO;
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
ENABLE_NS_ASSERTIONS = NO;
ENABLE_STRICT_OBJC_MSGSEND = YES;
GCC_C_LANGUAGE_STANDARD = gnu11;
GCC_NO_COMMON_BLOCKS = YES;
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
GCC_WARN_UNDECLARED_SELECTOR = YES;
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
MACOSX_DEPLOYMENT_TARGET = 10.13;
MTL_ENABLE_DEBUG_INFO = NO;
SDKROOT = macosx;
};
name = Release;
};
04C545FC21BE2AEB00EF280D /* Debug */ = {
isa = XCBuildConfiguration;
buildSettings = {
CODE_SIGN_STYLE = Automatic;
DEVELOPMENT_TEAM = 6TZ958XNMU;
GCC_PREPROCESSOR_DEFINITIONS = (
"DEBUG=1",
"$(inherited)",
DSO_DLFCN,
"CPU=\\\"amd64\\\"",
OS_DARWIN,
);
HEADER_SEARCH_PATHS = /System/Library/Frameworks/JavaVM.framework/Versions/A/Headers/;
OTHER_LDFLAGS = "";
PRODUCT_NAME = "$(TARGET_NAME)";
};
name = Debug;
};
04C545FD21BE2AEB00EF280D /* Release */ = {
isa = XCBuildConfiguration;
buildSettings = {
CODE_SIGN_STYLE = Automatic;
DEVELOPMENT_TEAM = 6TZ958XNMU;
HEADER_SEARCH_PATHS = /System/Library/Frameworks/JavaVM.framework/Versions/A/Headers/;
OTHER_LDFLAGS = "";
PRODUCT_NAME = "$(TARGET_NAME)";
};
name = Release;
};
/* End XCBuildConfiguration section */
/* Begin XCConfigurationList section */
04C545EF21BE2AEB00EF280D /* Build configuration list for PBXProject "gcc01" */ = {
isa = XCConfigurationList;
buildConfigurations = (
04C545F921BE2AEB00EF280D /* Debug */,
04C545FA21BE2AEB00EF280D /* Release */,
);
defaultConfigurationIsVisible = 0;
defaultConfigurationName = Release;
};
04C545FB21BE2AEB00EF280D /* Build configuration list for PBXNativeTarget "gcc01" */ = {
isa = XCConfigurationList;
buildConfigurations = (
04C545FC21BE2AEB00EF280D /* Debug */,
04C545FD21BE2AEB00EF280D /* Release */,
);
defaultConfigurationIsVisible = 0;
defaultConfigurationName = Release;
};
/* End XCConfigurationList section */
};
rootObject = 04C545EC21BE2AEB00EF280D /* Project object */;
}
/* 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 "jsvc.h"
#include <limits.h>
#include <glob.h>
/* Return the argument of a command line option */
static char *optional(int argc, char *argv[], int argi)
{
argi++;
if (argi >= argc)
return NULL;
if (argv[argi] == NULL)
return NULL;
if (argv[argi][0] == '-')
return NULL;
return strdup(argv[argi]);
}
static char *memstrcat(char *ptr, const char *str, const char *add)
{
size_t nl = 1;
int nas = ptr == NULL;
if (ptr)
nl += strlen(ptr);
if (str)
nl += strlen(str);
if (add)
nl += strlen(add);
ptr = (char *)realloc(ptr, nl);
if (ptr) {
if (nas)
*ptr = '\0';
if (str)
strcat(ptr, str);
if (add)
strcat(ptr, add);
}
return ptr;
}
static char* eval_ppath(char *strcp, const char *pattern)
{
glob_t globbuf;
char jars[PATH_MAX + 1];
if (strlen(pattern) > (sizeof(jars) - 5)) {
return memstrcat(strcp, pattern, NULL);
}
strcpy(jars, pattern);
strcat(jars, ".jar");
memset(&globbuf, 0, sizeof(glob_t));
if (glob(jars, GLOB_ERR, NULL, &globbuf) == 0) {
size_t n;
for (n = 0; n < globbuf.gl_pathc - 1; n++) {
strcp = memstrcat(strcp, globbuf.gl_pathv[n], ":");
if (strcp == NULL) {
globfree(&globbuf);
return NULL;
}
}
strcp = memstrcat(strcp, globbuf.gl_pathv[n], NULL);
globfree(&globbuf);
}
return strcp;
}
#define JAVA_CLASSPATH "-Djava.class.path="
/**
* Call glob on each PATH like string path.
* Glob is called only if the part ends with asterisk in which
* case asterisk is replaced by *.jar when searching
*/
static char* eval_cpath(const char *cp)
{
char *cpy = memstrcat(NULL, JAVA_CLASSPATH, cp);
char *gcp = NULL;
char *pos;
char *ptr;
if (!cpy)
return NULL;
ptr = cpy + sizeof(JAVA_CLASSPATH) - 1;;
while ((pos = strchr(ptr, ':'))) {
*pos = '\0';
if (gcp)
gcp = memstrcat(gcp, ":", NULL);
else
gcp = memstrcat(NULL, JAVA_CLASSPATH, NULL);
if ((pos > ptr) && (*(pos - 1) == '*')) {
if (!(gcp = eval_ppath(gcp, ptr))) {
/* Error.
* Return the original string processed so far.
*/
return cpy;
}
}
else
gcp = memstrcat(gcp, ptr, NULL);
ptr = pos + 1;
}
if (*ptr) {
size_t end = strlen(ptr);
if (gcp)
gcp = memstrcat(gcp, ":", NULL);
else
gcp = memstrcat(NULL, JAVA_CLASSPATH, NULL);
if (end > 0 && ptr[end - 1] == '*') {
/* Last path elemet ends with star
* Do a globbing.
*/
gcp = eval_ppath(gcp, ptr);
}
else {
/* Just add the part */
gcp = memstrcat(gcp, ptr, NULL);
}
}
/* Free the allocated copy */
if (gcp) {
free(cpy);
return gcp;
}
else
return cpy;
}
/* Parse command line arguments */
static arg_data *parse(int argc, char *argv[])
{
arg_data *args = NULL;
char *temp = NULL;
char *cmnd = NULL;
int x = 0;
/* Create the default command line arguments */
args = (arg_data *)malloc(sizeof(arg_data));
args->pidf = "/var/run/jsvc.pid"; /* The default PID file */
args->user = NULL; /* No user switching by default */
args->dtch = true; /* Do detach from parent */
args->vers = false; /* Don't display version */
args->help = false; /* Don't display help */
args->chck = false; /* Don't do a check-only startup */
args->stop = false; /* Stop a running jsvc */
args->wait = 0; /* Wait until jsvc has started the JVM */
args->restarts = -1; /* Infinite restarts by default */
args->install = false; /* Don't install as a service */
args->remove = false; /* Don't remove the installed service */
args->service = false; /* Don't run as a service */
args->name = NULL; /* No VM version name */
args->home = NULL; /* No default JAVA_HOME */
args->onum = 0; /* Zero arguments, but let's have some room */
args->clas = NULL; /* No class predefined */
args->anum = 0; /* Zero class specific arguments but make room*/
args->cwd = "/"; /* Use root as default */
args->outfile = "/dev/null"; /* Swallow by default */
args->errfile = "/dev/null"; /* Swallow by default */
args->redirectstdin = true; /* Redirect stdin to /dev/null by default */
args->procname = "jsvc.exec";
#ifndef JSVC_UMASK
args->umask = 0077;
#else
args->umask = JSVC_UMASK;
#endif
if (!(args->args = (char **)malloc(argc * sizeof(char *))))
return NULL;
if (!(args->opts = (char **)malloc(argc * sizeof(char *))))
return NULL;
/* Set up the command name */
cmnd = strrchr(argv[0],'/');
if (cmnd == NULL)
cmnd = argv[0];
else
cmnd++;
log_prog = strdup(cmnd);
/* Iterate thru command line arguments */
for (x = 1; x < argc; x++) {
if (!strcmp(argv[x], "-cp") ||
!strcmp(argv[x], "-classpath")) {
temp = optional(argc, argv, x++);
if (temp == NULL) {
log_error("Invalid classpath specified");
return NULL;
}
args->opts[args->onum] = eval_cpath(temp);
if (args->opts[args->onum] == NULL) {
log_error("Invalid classpath specified");
return NULL;
}
free(temp);
args->onum++;
}
else if (!strcmp(argv[x], "-jvm")) {
args->name = optional(argc, argv, x++);
if (args->name == NULL) {
log_error("Invalid Java VM name specified");
return NULL;
}
}
else if (!strcmp(argv[x], "-client")) {
args->name = strdup("client");
}
else if (!strcmp(argv[x], "-server")) {
args->name = strdup("server");
}
else if (!strcmp(argv[x], "-home") ||
!strcmp(argv[x], "-java-home")) {
args->home = optional(argc, argv, x++);
if (args->home == NULL) {
log_error("Invalid Java Home specified");
return NULL;
}
}
else if (!strcmp(argv[x], "-user")) {
args->user = optional(argc, argv, x++);
if (args->user == NULL) {
log_error("Invalid user name specified");
return NULL;
}
}
else if (!strcmp(argv[x], "-cwd")) {
args->cwd = optional(argc, argv, x++);
if (args->cwd == NULL) {
log_error("Invalid working directory specified");
return NULL;
}
}
else if (!strcmp(argv[x], "-version")) {
args->vers = true;
args->dtch = false;
}
else if (!strcmp(argv[x], "-showversion")) {
args->vershow = true;
}
else if (!strcmp(argv[x], "-?") ||
!strcmp(argv[x], "-help") ||
!strcmp(argv[x], "--help")) {
args->help = true;
args->dtch = false;
return args;
}
else if (!strcmp(argv[x], "-X")) {
log_error("Option -X currently unsupported");
log_error("Please use \"java -X\" to see your extra VM options");
}
else if (!strcmp(argv[x], "-debug")) {
log_debug_flag = true;
}
else if (!strcmp(argv[x], "-wait")) {
temp = optional(argc, argv, x++);
if (temp)
args->wait = atoi(temp);
if (args->wait < 10) {
log_error("Invalid wait time specified (min=10)");
return NULL;
}
}
else if (!strcmp(argv[x], "-restarts")) {
temp = optional(argc, argv, x++);
if (temp)
args->restarts = atoi(temp);
if (args->restarts < -1) {
log_error("Invalid max restarts [-1,0,...)");
return NULL;
}
}
else if (!strcmp(argv[x], "-umask")) {
temp = optional(argc, argv, x++);
if (temp == NULL) {
log_error("Invalid umask specified");
return NULL;
}
/* Parameter must be in octal */
args->umask = (int)strtol(temp, NULL, 8);
if (args->umask < 02) {
log_error("Invalid umask specified (min=02)");
return NULL;
}
}
else if (!strcmp(argv[x], "-stop")) {
args->stop = true;
}
else if (!strcmp(argv[x], "-check")) {
args->chck = true;
args->dtch = false;
}
else if (!strcmp(argv[x], "-nodetach")) {
args->dtch = false;
}
else if (!strcmp(argv[x], "-keepstdin")) {
args->redirectstdin = false;
}
else if (!strcmp(argv[x], "-service")) {
args->service = true;
}
else if (!strcmp(argv[x], "-install")) {
args->install = true;
}
else if (!strcmp(argv[x], "-remove")) {
args->remove = true;
}
else if (!strcmp(argv[x], "-pidfile")) {
args->pidf = optional(argc, argv, x++);
if (args->pidf == NULL) {
log_error("Invalid PID file specified");
return NULL;
}
}
else if (!strcmp(argv[x], "-outfile")) {
args->outfile = optional(argc, argv, x++);
if(args->outfile == NULL) {
log_error("Invalid Output File specified");
return NULL;
}
}
else if (!strcmp(argv[x], "-errfile")) {
args->errfile = optional(argc, argv, x++);
if (args->errfile == NULL) {
log_error("Invalid Error File specified");
return NULL;
}
}
else if (!strncmp(argv[x], "-verbose", 8)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strcmp(argv[x], "-D")) {
log_error("Parameter -D must be followed by <name>=<value>");
return NULL;
}
else if (!strncmp(argv[x], "-D", 2)) {
temp = strchr(argv[x], '=');
if (temp == argv[x] + 2) {
log_error("A property name must be specified before '='");
return NULL;
}
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-X", 2)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-ea", 3)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-enableassertions", 17)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-da", 3)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-disableassertions", 18)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strcmp(argv[x], "-esa")) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strcmp(argv[x], "-enablesystemassertions")) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strcmp(argv[x], "-dsa")) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strcmp(argv[x], "-disablesystemassertions")) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strcmp(argv[x], "-procname")) {
args->procname = optional(argc, argv, x++);
if (args->procname == NULL) {
log_error("Invalid process name specified");
return NULL;
}
}
else if (!strncmp(argv[x], "-agentlib:", 10)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-agentpath:", 11)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "-javaagent:", 11)) {
args->opts[args->onum++] = strdup(argv[x]);
}
/* Java 9 specific options */
else if (!strncmp(argv[x], "--add-modules=", 14)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--module-path=", 14)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--upgrade-module-path=", 22)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--add-reads=", 12)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--add-exports=", 14)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--add-opens=", 12)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--limit-modules=", 16)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--patch-module=", 15)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (!strncmp(argv[x], "--illegal-access=", 17)) {
args->opts[args->onum++] = strdup(argv[x]);
}
else if (*argv[x] == '-') {
log_error("Invalid option %s",argv[x]);
return NULL;
}
else {
args->clas=strdup(argv[x]);
break;
}
}
if (args->clas == NULL && args->remove == false) {
log_error("No class specified");
return NULL;
}
x++;
while (x < argc) {
args->args[args->anum++] = strdup(argv[x++]);
}
return args;
}
static const char *IsYesNo(bool par)
{
switch (par) {
case false:
return "No";
case true:
return "Yes";
}
return "[Error]";
}
static const char *IsTrueFalse(bool par)
{
switch (par) {
case false:
return "False";
case true:
return "True";
}
return "[Error]";
}
static const char *IsEnabledDisabled(bool par)
{
switch (par) {
case true:
return "Enabled";
case false:
return "Disabled";
}
return "[Error]";
}
/* Main entry point: parse command line arguments and dump them */
arg_data *arguments(int argc, char *argv[])
{
arg_data *args = parse(argc,argv);
int x = 0;
if (args == NULL) {
log_error("Cannot parse command line arguments");
return NULL;
}
if (log_debug_flag == true) {
log_debug("+-- DUMPING PARSED COMMAND LINE ARGUMENTS --------------");
log_debug("| Detach: %s", IsTrueFalse(args->dtch));
log_debug("| Show Version: %s", IsYesNo(args->vers));
log_debug("| Show Help: %s", IsYesNo(args->help));
log_debug("| Check Only: %s", IsEnabledDisabled(args->chck));
log_debug("| Stop: %s", IsTrueFalse(args->stop));
log_debug("| Wait: %d", args->wait);
log_debug("| Restarts: %d", args->restarts);
log_debug("| Run as service: %s", IsYesNo(args->service));
log_debug("| Install service: %s", IsYesNo(args->install));
log_debug("| Remove service: %s", IsYesNo(args->remove));
log_debug("| JVM Name: \"%s\"", PRINT_NULL(args->name));
log_debug("| Java Home: \"%s\"", PRINT_NULL(args->home));
log_debug("| PID File: \"%s\"", PRINT_NULL(args->pidf));
log_debug("| User Name: \"%s\"", PRINT_NULL(args->user));
log_debug("| Extra Options: %d", args->onum);
for (x = 0; x < args->onum; x++) {
log_debug("| \"%s\"", args->opts[x]);
}
log_debug("| Class Invoked: \"%s\"", PRINT_NULL(args->clas));
log_debug("| Class Arguments: %d", args->anum);
for (x = 0; x < args->anum; x++) {
log_debug("| \"%s\"",args->args[x]);
}
log_debug("+-------------------------------------------------------");
}
return args;
}
/* 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.
*/
#ifndef __JSVC_ARGUMENTS_H__
#define __JSVC_ARGUMENTS_H__
#ifdef __cplusplus
extern "C"
{
#endif
/**
* The structure holding all parsed command line options.
*/
typedef struct {
/** The name of the PID file. */
char *pidf;
/** The name of the user. */
char *user;
/** The name of the JVM to use. */
char *name;
/** The JDK or JRE installation path (JAVA_HOME). */
char *home;
/** Working directory (defaults to /). */
char *cwd;
/** Options used to invoke the JVM. */
char **opts;
/** Number of JVM options. */
int onum;
/** The name of the class to invoke. */
char *clas;
/** Command line arguments to the class. */
char **args;
/** Number of class command line arguments. */
int anum;
/** Wether to detach from parent process or not. */
bool dtch;
/** Wether to print the VM version number or not. */
bool vers;
/** Show the VM version and continue. */
bool vershow;
/** Wether to display the help page or not. */
bool help;
/** Only check environment without running the service. */
bool chck;
/** Stop running jsvc */
bool stop;
/** number of seconds to until service started */
int wait;
/** max restarts **/
int restarts;
/** Install as a service (win32) */
bool install;
/** Remove when installed as a service (win32) */
bool remove;
/** Run as a service (win32) */
bool service;
/** Destination for stdout */
char *outfile;
/** Destination for stderr */
char *errfile;
/** Program name **/
char *procname;
/** Whether to redirect stdin to /dev/null or not. Defaults to true **/
bool redirectstdin;
/** What umask to use **/
int umask;
} arg_data;
/**
* Parse command line arguments.
*
* @param argc The number of command line arguments.
* @param argv Pointers to the different arguments.
* @return A pointer to a arg_data structure containing the parsed command
* line arguments, or NULL if an error was detected.
*/
arg_data *arguments(int argc, char *argv[]);
#ifdef __cplusplus
}
#endif
#endif /* ifndef __JSVC_ARGUMENTS_H__ */
/* 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 "jsvc.h"
#include <sys/types.h>
#include <unistd.h>
#include <time.h>
/* Wether debug is enabled or not */
bool log_debug_flag = true;
/* Wether SYSLOG logging (for stderr) is enable or not. */
bool log_stderr_syslog_flag = true;
/* Wether SYSLOG logging (for stdout) is enable or not. */
bool log_stdout_syslog_flag = true;
/* The name of the jsvc binary. */
char *log_prog = "jsvc";
/* Dump a debug trace message to stderr */
void log_debug(const char *fmt, ...)
{
va_list ap;
time_t now;
struct tm *nowtm;
char buff[80];
if (log_debug_flag == false)
return;
if (fmt == NULL)
return;
now = time(NULL);
nowtm = localtime(&now);
strftime(buff, sizeof(buff), "%Y-%m-%d %T", nowtm);
va_start(ap, fmt);
if (log_stderr_syslog_flag)
fprintf(stderr, "%s %d %s debug: ", buff, getpid(), log_prog);
#if defined(DEBUG) || defined(_DEBUG)
else
fprintf(stderr, "[debug] %s %d ", buff, getpid());
#endif
vfprintf(stderr, fmt, ap);
fprintf(stderr, "\n");
fflush(stderr);
va_end(ap);
}
/* Dump an error message to stderr */
void log_error(const char *fmt, ...)
{
va_list ap;
time_t now;
struct tm *nowtm;
char buff[80];
if (fmt == NULL)
return;
va_start(ap, fmt);
if (log_stderr_syslog_flag) {
now = time(NULL);
nowtm = localtime(&now);
strftime(buff, sizeof(buff), "%Y-%m-%d %T", nowtm);
fprintf(stderr, "%s %d %s error: ", buff, getpid(), log_prog);
}
vfprintf(stderr, fmt, ap);
fprintf(stderr, "\n");
fflush(stderr);
va_end(ap);
}
/* 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.
*/
#ifndef __JSVC_DEBUG_H__
#define __JSVC_DEBUG_H__
#ifdef __cplusplus
extern "C" {
#endif
/**
* Wether debugging is enabled or not.
*/
extern bool log_debug_flag;
/* Wether SYSLOG logging (for stderr) is enable or not. */
extern bool log_stderr_syslog_flag;
/* Wether SYSLOG logging (for stdout) is enable or not. */
extern bool log_stdout_syslog_flag;
/**
* The name of the jsvc binary.
*/
extern char *log_prog;
/**
* Helper macro to avoid NPEs in printf.
*/
#define PRINT_NULL(x) ((x) == NULL ? "null" : (x))
/**
* Dump a debug message.
*
* @param fmt The printf style message format.
* @param ... Any optional parameter for the message.
*/
void log_debug(const char *fmt, ...);
/**
* Dump an error message.
*
* @param fmt The printf style message format.
* @param ... Any optional parameter for the message.
*/
void log_error(const char *fmt, ...);
#ifdef __cplusplus
}
#endif
#endif /* ifndef __JSVC_DEBUG_H__ */
/* 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 "jsvc.h"
#ifdef DSO_DLFCN
#include <dlfcn.h>
#ifdef OS_LINUX
bool ld_library_path_set = false;
#endif /* ifdef OS_LINUX */
/* Initialize all DSO stuff */
bool dso_init(void)
{
return true;
}
/* Attempt to link a library from a specified filename */
dso_handle dso_link(const char *path)
{
log_debug("Attemtping to load library %s", path);
return ((void *)dlopen(path, RTLD_GLOBAL | RTLD_NOW));
}
/* Attempt to unload a library */
bool dso_unlink(dso_handle libr)
{
if (dlclose(libr) == 0)
return true;
else
return false;
}
/* Get the address for a specifed symbol */
void *dso_symbol(dso_handle hdl, const char *nam)
{
return dlsym(hdl, nam);
}
/* Return the error message from dlopen */
char *dso_error(void)
{
return (dlerror());
}
#endif /* ifdef DSO_DLFCN */
/* 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.
*/
#ifndef __JSVC_DSO_H__
#define __JSVC_DSO_H__
#include "jsvc.h"
/**
* A library handle represents a unique pointer to its location in memory.
*/
#ifdef DSO_DYLD
#include <mach-o/dyld.h>
#endif
typedef void *dso_handle;
bool dso_init(void);
dso_handle dso_link(const char *pth);
bool dso_unlink(dso_handle lib);
void *dso_symbol(dso_handle lib, const char *nam);
char *dso_error(void);
#endif /* __JSVC_DSO_H__ */
/* 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 "jsvc.h"
void help(home_data *data)
{
int x;
printf("Usage: %s [-options] class [args...]\n", log_prog);
printf("\n");
printf("Where options include:\n");
printf("\n");
printf(" -help | --help | -?\n");
printf(" show this help page (implies -nodetach)\n");
printf(" -jvm <JVM name>\n");
printf(" use a specific Java Virtual Machine. Available JVMs:\n");
printf(" ");
for (x = 0; x < data->jnum; x++) {
printf(" '%s'", PRINT_NULL(data->jvms[x]->name));
}
printf("\n");
printf(" -client\n");
printf(" use a client Java Virtual Machine.\n");
printf(" -server\n");
printf(" use a server Java Virtual Machine.\n");
printf(" -cp | -classpath <directories and zip/jar files>\n");
printf(" set search path for service classes and resouces\n");
printf(" -java-home | -home <directory>\n");
printf(" set the path of your JDK or JRE installation (or set\n");
printf(" the JAVA_HOME environment variable)\n");
printf(" -version\n");
printf(" show the current Java environment version (to check\n");
printf(" correctness of -home and -jvm. Implies -nodetach)\n");
printf(" -showversion\n");
printf(" show the current Java environment version (to check\n");
printf(" correctness of -home and -jvm) and continue execution.\n");
printf(" -nodetach\n");
printf(" don't detach from parent process and become a daemon\n");
printf(" -debug\n");
printf(" verbosely print debugging information\n");
printf(" -check\n");
printf(" only check service (implies -nodetach)\n");
printf(" -user <user>\n");
printf(" user used to run the daemon (defaults to current user)\n");
printf(" -verbose[:class|gc|jni]\n");
printf(" enable verbose output\n");
printf(" -cwd </full/path>\n");
printf(" set working directory to given location (defaults to /)\n");
printf(" -outfile </full/path/to/file>\n");
printf(" Location for output from stdout (defaults to /dev/null)\n");
printf(" Use the value '&2' to simulate '1>&2'\n");
printf(" -errfile </full/path/to/file>\n");
printf(" Location for output from stderr (defaults to /dev/null)\n");
printf(" Use the value '&1' to simulate '2>&1'\n");
printf(" -pidfile </full/path/to/file>\n");
printf(" Location for output from the file containing the pid of jsvc\n");
printf(" (defaults to /var/run/jsvc.pid)\n");
printf(" -D<name>=<value>\n");
printf(" set a Java system property\n");
printf(" -X<option>\n");
printf(" set Virtual Machine specific option\n");
printf(" -ea[:<packagename>...|:<classname>]\n");
printf(" -enableassertions[:<packagename>...|:<classname>]\n");
printf(" enable assertions\n");
printf(" -da[:<packagename>...|:<classname>]\n");
printf(" -disableassertions[:<packagename>...|:<classname>]\n");
printf(" disable assertions\n");
printf(" -esa | -enablesystemassertions\n");
printf(" enable system assertions\n");
printf(" -dsa | -disablesystemassertions\n");
printf(" disable system assertions\n");
printf(" -agentlib:<libname>[=<options>]\n");
printf(" load native agent library <libname>, e.g. -agentlib:hprof\n");
printf(" -agentpath:<pathname>[=<options>]\n");
printf(" load native agent library by full pathname\n");
printf(" -javaagent:<jarpath>[=<options>]\n");
printf(" load Java programming language agent, see java.lang.instrument\n");
printf(" -procname <procname>\n");
printf(" use the specified process name\n");
printf(" -wait <waittime>\n");
printf(" wait waittime seconds for the service to start\n");
printf(" waittime should multiple of 10 (min=10)\n");
printf(" -restarts <maxrestarts>\n");
printf(" maximum automatic restarts (integer)\n");
printf(" -1=infinite (default), 0=none, 1..(INT_MAX-1)=fixed restart count\n");
printf(" -stop\n");
printf(" stop the service using the file given in the -pidfile option\n");
printf(" -keepstdin\n");
printf(" does not redirect stdin to /dev/null\n");
printf(" --add-modules=<module name>\n");
printf(" Java 9 --add-modules option. Passed as it is to JVM\n");
printf(" --module-path=<module path>\n");
printf(" Java 9 --module-path option. Passed as it is to JVM\n");
printf(" --upgrade-module-path=<module path>\n");
printf(" Java 9 --upgrade-module-path option. Passed as it is to JVM\n");
printf(" --add-reads=<module name>\n");
printf(" Java 9 --add-reads option. Passed as it is to JVM\n");
printf(" --add-exports=<module name>\n");
printf(" Java 9 --add-exports option. Passed as it is to JVM\n");
printf(" --add-opens=<module name>\n");
printf(" Java 9 --add-opens option. Passed as it is to JVM\n");
printf(" --limit-modules=<module name>\n");
printf(" Java 9 --limit-modules option. Passed as it is to JVM\n");
printf(" --patch-module=<module name>\n");
printf(" Java 9 --patch-module option. Passed as it is to JVM\n");
printf(" --illegal-access=<value>\n");
printf(" Java 9 --illegal-access option. Passed as it is to JVM. Refer java help for possible values.\n");
printf("\njsvc (Apache Commons Daemon) " JSVC_VERSION_STRING "\n");
printf("Copyright (c) 1999-2017 Apache Software Foundation.\n");
printf("\n");
}
/* 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.
*/
#ifndef __JSVC_HELP_H__
#define __JSVC_HELP_H__
void help(home_data *data);
#endif /* __JSVC_HELP_H__ */
/*
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 "jsvc.h"
/* Check if a path is a directory */
static bool checkdir(char *path)
{
struct stat home;
if (path == NULL)
return (false);
if (stat(path, &home) != 0)
return (false);
if (S_ISDIR(home.st_mode))
return (true);
return (false);
}
/* Check if a path is a file */
static bool checkfile(char *path)
{
struct stat home;
if (path == NULL)
return (false);
if (stat(path, &home) != 0)
return (false);
if (S_ISREG(home.st_mode))
return (true);
return (false);
}
/* Parse a VM configuration file */
static bool parse(home_data *data)
{
FILE *cfgf = fopen(data->cfgf, "r");
char *ret = NULL, *sp;
char buf[1024];
if (cfgf == NULL) {
log_debug("Can't open %s\n", data->cfgf);
return (false);
}
data->jvms = (home_jvm **)malloc(256 * sizeof(home_jvm *));
while ((ret = fgets(buf, 1024, cfgf)) != NULL) {
char *tmp = strchr(ret, '#');
int pos;
/* Clear the string at the first occurrence of '#' */
if (tmp != NULL)
tmp[0] = '\0';
/* Trim the string (including leading '-' chars */
while ((ret[0] == ' ') || (ret[0] == '\t') || (ret[0] == '-'))
ret++;
pos = strlen(ret);
while (pos >= 0) {
if ((ret[pos] == '\r') || (ret[pos] == '\n') || (ret[pos] == '\t')
|| (ret[pos] == '\0') || (ret[pos] == ' ')) {
ret[pos--] = '\0';
}
else
break;
}
/* Format changed for 1.4 JVMs */
sp = strchr(ret, ' ');
if (sp != NULL)
*sp = '\0';
/* Did we find something significant? */
if (strlen(ret) > 0) {
char *libf = NULL;
int x = 0;
log_debug("Found VM %s definition in configuration", ret);
while (location_jvm_configured[x] != NULL) {
char *orig = location_jvm_configured[x];
char temp[1024];
char repl[1024];
int k;
k = replace(temp, 1024, orig, "$JAVA_HOME", data->path);
if (k != 0) {
log_error("Can't replace home in VM library (%d)", k);
return (false);
}
k = replace(repl, 1024, temp, "$VM_NAME", ret);
if (k != 0) {
log_error("Can't replace name in VM library (%d)", k);
return (false);
}
log_debug("Checking library %s", repl);
if (checkfile(repl)) {
libf = strdup(repl);
break;
}
x++;
}
if (libf == NULL) {
log_debug("Cannot locate library for VM %s (skipping)", ret);
}
else {
data->jvms[data->jnum] = (home_jvm *)malloc(sizeof(home_jvm));
data->jvms[data->jnum]->name = strdup(ret);
data->jvms[data->jnum]->libr = libf;
data->jnum++;
data->jvms[data->jnum] = NULL;
}
}
}
fclose(cfgf);
return (true);
}
/* Build a Java Home structure for a path */
static home_data *build(char *path)
{
home_data *data = NULL;
char *cfgf = NULL;
char buf[1024];
int x = 0;
int k = 0;
if (path == NULL)
return (NULL);
log_debug("Attempting to locate Java Home in %s", path);
if (checkdir(path) == false) {
log_debug("Path %s is not a directory", path);
return (NULL);
}
while (location_jvm_cfg[x] != NULL) {
if ((k =
replace(buf, 1024, location_jvm_cfg[x], "$JAVA_HOME",
path)) != 0) {
log_error("Error replacing values for jvm.cfg (%d)", k);
return (NULL);
}
log_debug("Attempting to locate VM configuration file %s", buf);
if (checkfile(buf) == true) {
log_debug("Found VM configuration file at %s", buf);
cfgf = strdup(buf);
break;
}
x++;
}
data = (home_data *)malloc(sizeof(home_data));
data->path = strdup(path);
data->cfgf = cfgf;
data->jvms = NULL;
data->jnum = 0;
/* We don't have a jvm.cfg configuration file, so all we have to do is
trying to locate the "default" Java Virtual Machine library */
if (cfgf == NULL) {
log_debug("VM configuration file not found");
x = 0;
while (location_jvm_default[x] != NULL) {
char *libr = location_jvm_default[x];
if ((k = replace(buf, 1024, libr, "$JAVA_HOME", path)) != 0) {
log_error("Error replacing values for JVM library (%d)", k);
return (NULL);
}
log_debug("Attempting to locate VM library %s", buf);
if (checkfile(buf) == true) {
data->jvms = (home_jvm **)malloc(2 * sizeof(home_jvm *));
data->jvms[0] = (home_jvm *)malloc(sizeof(home_jvm));
data->jvms[0]->name = NULL;
data->jvms[0]->libr = strdup(buf);
data->jvms[1] = NULL;
data->jnum = 1;
return (data);
}
x++;
}
return (data);
}
/* If we got here, we most definitely found a jvm.cfg file */
if (parse(data) == false) {
log_error("Cannot parse VM configuration file %s", data->cfgf);
}
return (data);
}
/* Find the Java Home */
static home_data *find(char *path)
{
home_data *data = NULL;
int x = 0;
if (path == NULL || *path == '\0' || strcmp(path, "/") == 0) {
log_debug("Home not specified on command line, using environment");
path = getenv("JAVA_HOME");
if (path == NULL || *path == '\0' || strcmp(path, "/") == 0) {
/* guard against empty JAVA_HOME */
path = NULL;
}
}
if (path == NULL) {
log_debug("Home not on command line or in environment, searching");
while (location_home[x] != NULL) {
if ((data = build(location_home[x])) != NULL) {
log_debug("Java Home located in %s", data->path);
return (data);
}
x++;
}
}
else {
if ((data = build(path)) != NULL) {
log_debug("Java Home located in %s", data->path);
return (data);
}
}
return (NULL);
}
/* Main entry point: locate home and dump structure */
home_data *home(char *path)
{
home_data *data = find(path);
int x = 0;
if (data == NULL) {
log_error("Cannot locate Java Home");
return (NULL);
}
if (log_debug_flag == true) {
log_debug("+-- DUMPING JAVA HOME STRUCTURE ------------------------");
log_debug("| Java Home: \"%s\"", PRINT_NULL(data->path));
log_debug("| Java VM Config.: \"%s\"", PRINT_NULL(data->cfgf));
log_debug("| Found JVMs: %d", data->jnum);
for (x = 0; x < data->jnum; x++) {
home_jvm *jvm = data->jvms[x];
log_debug("| JVM Name: \"%s\"", PRINT_NULL(jvm->name));
log_debug("| \"%s\"", PRINT_NULL(jvm->libr));
}
log_debug("+-------------------------------------------------------");
}
return (data);
}
/*
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.
*/
#ifndef __JSVC_HOME_H__
#define __JSVC_HOME_H__
typedef struct home_jvm home_jvm;
typedef struct home_data home_data;
struct home_jvm
{
char *name;
char *libr;
};
struct home_data
{
char *path;
char *cfgf;
home_jvm **jvms;
int jnum;
};
/**
* Attempt to locate a Java Home directory and build its structure.
*
* @param path The java home path specified on the command line.
* @return A home_data structure containing all informations related to
* the Java environment, or NULL if no home was found.
*/
home_data *home(char *path);
#endif /* ifndef __JSVC_HOME_H__ */
/* 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 "jsvc.h"
#ifdef OS_CYGWIN
typedef long long __int64;
#endif
#include <unistd.h>
#include <jni.h>
#ifdef CHARSET_EBCDIC
#ifdef OSD_POSIX
#include <ascii_ebcdic.h>
#define jsvc_xlate_to_ascii(b) _e2a(b)
#define jsvc_xlate_from_ascii(b) _a2e(b)
#endif
#else
#define jsvc_xlate_to_ascii(b) /* NOOP */
#define jsvc_xlate_from_ascii(b) /* NOOP */
#endif
static JavaVM *jvm = NULL;
static JNIEnv *env = NULL;
static jclass cls = NULL;
#define FALSE 0
#define TRUE !FALSE
static void shutdown(JNIEnv *env, jobject source, jboolean reload)
{
log_debug("Shutdown requested (reload is %d)", reload);
if (reload == TRUE)
main_reload();
else
main_shutdown();
}
static void failed(JNIEnv *env, jobject source, jstring message)
{
if (message) {
const char *msg = (*env)->GetStringUTFChars(env, message, NULL);
log_error("Failed %s", msg ? msg : "(null)");
if (msg)
(*env)->ReleaseStringUTFChars(env, message, msg);
}
else
log_error("Failed requested");
main_shutdown();
}
/* Automatically restart when the JVM crashes */
static void java_abort123(void)
{
exit(123);
}
char *java_library(arg_data *args, home_data *data)
{
char *libf = NULL;
/* Did we find ANY virtual machine? */
if (data->jnum == 0) {
log_error("Cannot find any VM in Java Home %s", data->path);
return NULL;
}
/* Select the VM */
if (args->name == NULL) {
libf = data->jvms[0]->libr;
log_debug("Using default JVM in %s", libf);
}
else {
int x;
for (x = 0; x < data->jnum; x++) {
if (data->jvms[x]->name == NULL)
continue;
if (strcmp(args->name, data->jvms[x]->name) == 0) {
libf = data->jvms[x]->libr;
log_debug("Using specific JVM in %s", libf);
break;
}
}
if (libf == NULL) {
log_error("Invalid JVM name specified %s", args->name);
return NULL;
}
}
return libf;
}
typedef jint (*jvm_create_t)(JavaVM **, JNIEnv **, JavaVMInitArgs *);
bool java_signal(void)
{
jmethodID method;
jboolean ret;
char start[] = "signal";
char startparams[] = "()Z";
jsvc_xlate_to_ascii(start);
jsvc_xlate_to_ascii(startparams);
method = (*env)->GetStaticMethodID(env, cls, start, startparams);
if (method == NULL) {
(*env)->ExceptionClear(env);
log_error("Cannot find DaemonLoader \"signal\" method");
return false;
}
ret = (*env)->CallStaticBooleanMethod(env, cls, method);
/* Clear any pending exception
* so we can continue calling native methods
*/
(*env)->ExceptionClear(env);
log_debug("Daemon signal method returned %s", ret ? "true" : "false");
return ret;
}
/* Initialize the JVM and its environment, loading libraries and all */
bool java_init(arg_data *args, home_data *data)
{
#ifdef OS_DARWIN
dso_handle apph = NULL;
char appf[1024];
struct stat sb;
#endif /* ifdef OS_DARWIN */
jvm_create_t symb = NULL;
JNINativeMethod nativemethods[2];
JavaVMOption *opt = NULL;
dso_handle libh = NULL;
JavaVMInitArgs arg;
char *libf = NULL;
jint ret;
int x;
char loaderclass[] = LOADER;
char shutdownmethod[] = "shutdown";
char shutdownparams[] = "(Z)V";
char failedmethod[] = "failed";
char failedparams[] = "(Ljava/lang/String;)V";
char daemonprocid[64];
/* Decide WHAT virtual machine we need to use */
libf = java_library(args, data);
if (libf == NULL) {
log_error("Cannot locate JVM library file");
return false;
}
/* Initialize the DSO library */
if (dso_init() != true) {
log_error("Cannot initialize the dynamic library loader");
return false;
}
/* Load the JVM library */
#if !defined(OSD_POSIX)
libh = dso_link(libf);
if (libh == NULL) {
log_error("Cannot dynamically link to %s", libf);
log_error("%s", dso_error());
return false;
}
log_debug("JVM library %s loaded", libf);
#endif
#ifdef OS_DARWIN
/*
MacOS/X actually has two libraries, one with the REAL vm, and one for
the VM startup.
- JVM 1.6, the library name is libverify.dylib
- JVM 1.7 onwards, the library name is libjli.dylib
*/
if (replace(appf, 1024, "$JAVA_HOME/../Libraries/libverify.dylib",
"$JAVA_HOME", data->path) != 0) {
log_error("Cannot replace values in loader library");
return false;
}
if (stat(appf, &sb)) {
if (replace(appf, 1024, "$JAVA_HOME/../MacOS/libjli.dylib",
"$JAVA_HOME", data->path) != 0) {
log_error("Cannot replace values in loader library");
return false;
}
}
apph = dso_link(appf);
if (apph == NULL) {
log_error("Cannot load required shell library %s", appf);
return false;
}
log_debug("Shell library %s loaded", appf);
#endif /* ifdef OS_DARWIN */
#if defined(OSD_POSIX)
/* BS2000 does not allow to call JNI_CreateJavaVM indirectly */
#else
symb = (jvm_create_t)dso_symbol(libh, "JNI_CreateJavaVM");
if (symb == NULL) {
#ifdef OS_DARWIN
symb = (jvm_create_t)dso_symbol(apph, "JNI_CreateJavaVM");
if (symb == NULL) {
#endif /* ifdef OS_DARWIN */
log_error("Cannot find JVM library entry point");
return false;
#ifdef OS_DARWIN
}
#endif /* ifdef OS_DARWIN */
}
log_debug("JVM library entry point found (0x%08X)", symb);
#endif
/* Prepare the VM initialization arguments */
/* Minimum Java version is Java 6 */
arg.version = JNI_VERSION_1_6;
#if defined(OSD_POSIX)
if (JNI_GetDefaultJavaVMInitArgs(&arg) < 0) {
log_error("Cannot init default JVM default args");
return false;
}
#endif
arg.ignoreUnrecognized = FALSE;
arg.nOptions = args->onum + 4; /* pid, ppid and abort */
opt = (JavaVMOption *) malloc(arg.nOptions * sizeof(JavaVMOption));
for (x = 0; x < args->onum; x++) {
opt[x].optionString = strdup(args->opts[x]);
jsvc_xlate_to_ascii(opt[x].optionString);
opt[x].extraInfo = NULL;
}
/* Add our daemon process id */
snprintf(daemonprocid, sizeof(daemonprocid),
"-Dcommons.daemon.process.id=%d", (int)getpid());
opt[x].optionString = strdup(daemonprocid);
jsvc_xlate_to_ascii(opt[x].optionString);
opt[x++].extraInfo = NULL;
snprintf(daemonprocid, sizeof(daemonprocid),
"-Dcommons.daemon.process.parent=%d", (int)getppid());
opt[x].optionString = strdup(daemonprocid);
jsvc_xlate_to_ascii(opt[x].optionString);
opt[x++].extraInfo = NULL;
snprintf(daemonprocid, sizeof(daemonprocid),
"-Dcommons.daemon.version=%s", JSVC_VERSION_STRING);
opt[x].optionString = strdup(daemonprocid);
jsvc_xlate_to_ascii(opt[x].optionString);
opt[x++].extraInfo = NULL;
opt[x].optionString = strdup("abort");
jsvc_xlate_to_ascii(opt[x].optionString);
opt[x].extraInfo = (void *)java_abort123;
arg.options = opt;
/* Do some debugging */
if (log_debug_flag == true) {
log_debug("+-- DUMPING JAVA VM CREATION ARGUMENTS -----------------");
log_debug("| Version: %#08x", arg.version);
log_debug("| Ignore Unrecognized Arguments: %s",
arg.ignoreUnrecognized == TRUE ? "True" : "False");
log_debug("| Extra options: %d", args->onum);
for (x = 0; x < args->onum; x++) {
jsvc_xlate_from_ascii(opt[x].optionString);
log_debug("| \"%s\" (0x%08x)", opt[x].optionString,
opt[x].extraInfo);
jsvc_xlate_to_ascii(opt[x].optionString);
}
log_debug("+-------------------------------------------------------");
log_debug("| Internal options: %d", arg.nOptions - args->onum);
for (; x < arg.nOptions; x++) {
jsvc_xlate_from_ascii(opt[x].optionString);
log_debug("| \"%s\" (0x%08x)", opt[x].optionString,
opt[x].extraInfo);
jsvc_xlate_to_ascii(opt[x].optionString);
}
log_debug("+-------------------------------------------------------");
}
/* And finally create the Java VM */
#if defined(OSD_POSIX)
ret = JNI_CreateJavaVM(&jvm, &env, &arg);
#else
ret = (*symb) (&jvm, &env, &arg);
#endif
if (ret < 0) {
log_error("Cannot create Java VM");
return false;
}
log_debug("Java VM created successfully");
jsvc_xlate_to_ascii(loaderclass);
cls = (*env)->FindClass(env, loaderclass);
jsvc_xlate_from_ascii(loaderclass);
if (cls == NULL) {
log_error("Cannot find daemon loader %s", loaderclass);
return false;
}
log_debug("Class %s found", loaderclass);
jsvc_xlate_to_ascii(shutdownmethod);
nativemethods[0].name = shutdownmethod;
jsvc_xlate_to_ascii(shutdownparams);
nativemethods[0].signature = shutdownparams;
nativemethods[0].fnPtr = (void *)shutdown;
jsvc_xlate_to_ascii(failedmethod);
nativemethods[1].name = failedmethod;
jsvc_xlate_to_ascii(failedparams);
nativemethods[1].signature = failedparams;
nativemethods[1].fnPtr = (void *)failed;
if ((*env)->RegisterNatives(env, cls, nativemethods, 2) != 0) {
log_error("Cannot register native methods");
return false;
}
log_debug("Native methods registered");
return true;
}
/* Destroy the Java VM */
bool JVM_destroy(int exit)
{
jclass system = NULL;
jmethodID method;
char System[] = "java/lang/System";
char exitclass[] = "exit";
char exitparams[] = "(I)V";
jsvc_xlate_to_ascii(System);
system = (*env)->FindClass(env, System);
jsvc_xlate_from_ascii(System);
if (system == NULL) {
log_error("Cannot find class %s", System);
return false;
}
jsvc_xlate_to_ascii(exitclass);
jsvc_xlate_to_ascii(exitparams);
method = (*env)->GetStaticMethodID(env, system, exitclass, exitparams);
if (method == NULL) {
log_error("Cannot find \"System.exit(int)\" entry point");
return false;
}
log_debug("Calling System.exit(%d)", exit);
(*env)->CallStaticVoidMethod(env, system, method, (jint) exit);
/* We shouldn't get here, but just in case... */
log_debug("Destroying the Java VM");
if ((*jvm)->DestroyJavaVM(jvm) != 0)
return false;
log_debug("Java VM destroyed");
return true;
}
/* Call the load method in our DaemonLoader class */
bool java_load(arg_data *args)
{
jclass stringClass = NULL;
jstring className = NULL;
jstring currentArgument = NULL;
jobjectArray stringArray = NULL;
jmethodID method = NULL;
jboolean ret = FALSE;
int x;
char lang[] = "java/lang/String";
char load[] = "load";
char loadparams[] = "(Ljava/lang/String;[Ljava/lang/String;)Z";
jsvc_xlate_to_ascii(args->clas);
className = (*env)->NewStringUTF(env, args->clas);
jsvc_xlate_from_ascii(args->clas);
if (className == NULL) {
log_error("Cannot create string for class name");
return false;
}
jsvc_xlate_to_ascii(lang);
stringClass = (*env)->FindClass(env, lang);
if (stringClass == NULL) {
log_error("Cannot find class java/lang/String");
return false;
}
stringArray = (*env)->NewObjectArray(env, args->anum, stringClass, NULL);
if (stringArray == NULL) {
log_error("Cannot create arguments array");
return false;
}
for (x = 0; x < args->anum; x++) {
jsvc_xlate_to_ascii(args->args[x]);
currentArgument = (*env)->NewStringUTF(env, args->args[x]);
if (currentArgument == NULL) {
jsvc_xlate_from_ascii(args->args[x]);
log_error("Cannot create string for argument %s", args->args[x]);
return false;
}
(*env)->SetObjectArrayElement(env, stringArray, x, currentArgument);
}
jsvc_xlate_to_ascii(load);
jsvc_xlate_to_ascii(loadparams);
method = (*env)->GetStaticMethodID(env, cls, load, loadparams);
if (method == NULL) {
log_error("Cannot find Daemon Loader \"load\" entry point");
return false;
}
log_debug("Daemon loading...");
ret = (*env)->CallStaticBooleanMethod(env, cls, method, className,
stringArray);
if (ret == FALSE) {
log_error("Cannot load daemon");
return false;
}
log_debug("Daemon loaded successfully");
return true;
}
/* Call the start method in our daemon loader */
bool java_start(void)
{
jmethodID method;
jboolean ret;
char start[] = "start";
char startparams[] = "()Z";
jsvc_xlate_to_ascii(start);
jsvc_xlate_to_ascii(startparams);
method = (*env)->GetStaticMethodID(env, cls, start, startparams);
if (method == NULL) {
log_error("Cannot find Daemon Loader \"start\" entry point");
return false;
}
ret = (*env)->CallStaticBooleanMethod(env, cls, method);
if (ret == FALSE) {
log_error("Cannot start daemon");
return false;
}
log_debug("Daemon started successfully");
return true;
}
/*
* call the java sleep to prevent problems with threads
*/
void java_sleep(int wait)
{
jclass clsThread;
jmethodID method;
char jsleep[] = "sleep";
char jsleepparams[] = "(J)V";
char jthread[] = "java/lang/Thread";
jsvc_xlate_to_ascii(jsleep);
jsvc_xlate_to_ascii(jsleepparams);
jsvc_xlate_to_ascii(jthread);
clsThread = (*env)->FindClass(env, jthread);
if (clsThread == NULL) {
log_error("Cannot find java/lang/Thread class");
return;
}
method = (*env)->GetStaticMethodID(env, clsThread, jsleep, jsleepparams);
if (method == NULL) {
log_error("Cannot found the sleep entry point");
return;
}
(*env)->CallStaticVoidMethod(env, clsThread, method, (jlong) wait * 1000);
}
/* Call the stop method in our daemon loader */
bool java_stop(void)
{
jmethodID method;
jboolean ret;
char stop[] = "stop";
char stopparams[] = "()Z";
jsvc_xlate_to_ascii(stop);
jsvc_xlate_to_ascii(stopparams);
method = (*env)->GetStaticMethodID(env, cls, stop, stopparams);
if (method == NULL) {
log_error("Cannot found Daemon Loader \"stop\" entry point");
return false;
}
ret = (*env)->CallStaticBooleanMethod(env, cls, method);
if (ret == FALSE) {
log_error("Cannot stop daemon");
return false;
}
log_debug("Daemon stopped successfully");
return true;
}
/* Call the version method in our daemon loader */
bool java_version(void)
{
jmethodID method;
char version[] = "version";
char versionparams[] = "()V";
jsvc_xlate_to_ascii(version);
jsvc_xlate_to_ascii(versionparams);
method = (*env)->GetStaticMethodID(env, cls, version, versionparams);
if (method == NULL) {
log_error("Cannot found Daemon Loader \"version\" entry point");
return false;
}
(*env)->CallStaticVoidMethod(env, cls, method);
return true;
}
/* Call the check method in our DaemonLoader class */
bool java_check(arg_data *args)
{
jstring className = NULL;
jmethodID method = NULL;
jboolean ret = FALSE;
char check[] = "check";
char checkparams[] = "(Ljava/lang/String;)Z";
log_debug("Checking daemon");
jsvc_xlate_to_ascii(args->clas);
className = (*env)->NewStringUTF(env, args->clas);
jsvc_xlate_from_ascii(args->clas);
if (className == NULL) {
log_error("Cannot create string for class name");
return false;
}
jsvc_xlate_to_ascii(check);
jsvc_xlate_to_ascii(checkparams);
method = (*env)->GetStaticMethodID(env, cls, check, checkparams);
if (method == NULL) {
log_error("Cannot found Daemon Loader \"check\" entry point");
return false;
}
ret = (*env)->CallStaticBooleanMethod(env, cls, method, className);
if (ret == FALSE) {
log_error("An error was detected checking the %s daemon", args->clas);
return false;
}
log_debug("Daemon checked successfully");
return true;
}
/* Call the destroy method in our daemon loader */
bool java_destroy(void)
{
jmethodID method;
jboolean ret;
char destroy[] = "destroy";
char destroyparams[] = "()Z";
jsvc_xlate_to_ascii(destroy);
jsvc_xlate_to_ascii(destroyparams);
method = (*env)->GetStaticMethodID(env, cls, destroy, destroyparams);
if (method == NULL) {
log_error("Cannot found Daemon Loader \"destroy\" entry point");
return false;
}
ret = (*env)->CallStaticBooleanMethod(env, cls, method);
if (ret == FALSE) {
log_error("Cannot destroy daemon");
return false;
}
log_debug("Daemon destroyed successfully");
return true;
}
/* 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.
*/
#ifndef __JSVC_JAVA_H__
#define __JSVC_JAVA_H__
#define LOADER "org/apache/commons/daemon/support/DaemonLoader"
char *java_library(arg_data *args, home_data *data);
bool java_init(arg_data *args, home_data *data);
bool java_destroy(void);
bool java_load(arg_data *args);
bool java_signal(void);
bool java_start(void);
bool java_stop(void);
bool java_version(void);
bool java_check(arg_data *args);
bool JVM_destroy(int exit);
#endif /* __JSVC_JAVA_H__ */
此差异已折叠。
/* 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.
*/
#ifndef __JSVC_H__
#define __JSVC_H__
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
/* Definitions for booleans */
#ifdef OS_DARWIN
#include <stdbool.h>
#else
typedef enum {
false,
true
} bool;
#endif
#include "version.h"
#include "debug.h"
#include "arguments.h"
#include "home.h"
#include "location.h"
#include "replace.h"
#include "dso.h"
#include "java.h"
#include "help.h"
#include "signals.h"
#include "locks.h"
int main(int argc, char *argv[]);
void main_reload(void);
void main_shutdown(void);
#endif /* ifndef __JSVC_H__ */
/* 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 "jsvc.h"
/* Locations of various JVM files. We have to deal with all this madness since
* we're not distributed together (yet!) with an official VM distribution. All
* this CRAP needs improvement, and based on the observation of default
* distributions of VMs and OSes. If it doesn't work for you, please report
* your VM layout (ls -laR) and system details (build/config.guess) so that we
* can improve the search algorithms.
*/
/* If JAVA_HOME is not defined we search this list of paths (OS-dependent)
* to find the default location of the JVM.
*/
char *location_home[] = {
#if defined(OS_DARWIN)
"/System/Library/Frameworks/JavaVM.framework/Home",
"/System/Library/Frameworks/JavaVM.framework/Versions/CurrentJDK/Home/",
#elif defined(OS_LINUX) || defined(OS_SOLARIS) || defined(OS_BSD) || defined(OS_AIX)
"/usr/java/default",
"/usr/java",
"/usr/local/java",
"/usr/lib/jvm/default-java",
"/usr/lib/jvm/java",
"/etc/alternatives/java_sdk",
"/etc/alternatives/java_sdk_openjdk",
"/etc/alternatives/jre",
#if defined(__LP64__)
"/lib64/jvm/java",
"/lib64/jvm/java-openjdk",
#endif
"/lib/jvm/java",
"/lib/jvm/java-openjdk",
#elif defined(OS_CYGWIN)
"/cygdrive/c/WINNT/system32/java",
#elif defined(OS_SYSV)
"/opt/java",
"/opt/java/jdk13",
#elif defined(OS_TRU64)
"/usr/opt/java142",
"/usr/opt/java13",
#elif defined(OS_HPUX)
"/opt/java6",
"/opt/java1.5",
"/opt/java1.4",
"/opt/java1.3",
#endif
NULL,
};
/* The jvm.cfg file defines the VMs available for invocation. So far, on all
* all systems I've seen it's in $JAVA_HOME/lib. If this file is not found,
* then the "default" VMs (from location_jvm_default) is searched, otherwise,
* we're going to look thru the "configured" VMs (from lod_cfgvm) lying
* somewhere around JAVA_HOME. (Only two, I'm happy)
*/
char *location_jvm_cfg[] = {
"$JAVA_HOME/jre/lib/jvm.cfg", /* JDK */
"$JAVA_HOME/lib/jvm.cfg", /* JRE */
"$JAVA_HOME/jre/lib/" CPU "/jvm.cfg", /* JDK */
"$JAVA_HOME/lib/" CPU "/jvm.cfg", /* JRE */
#if defined(OS_AIX)
"$JAVA_HOME/jre/lib/ppc/jvm.cfg", /* JDK */
"$JAVA_HOME/lib/ppc/jvm.cfg", /* JRE */
#endif
NULL,
};
/* This is the list of "defaults" VM (searched when jvm.cfg is not found, as
* in the case of most JDKs 1.2.2
*/
char *location_jvm_default[] = {
#if defined(OS_DARWIN)
"$JAVA_HOME/../Libraries/libjvm.dylib",
"$JAVA_HOME/jre/lib/server/libjvm.dylib",
"$JAVA_HOME/jre/lib/client/libjvm.dylib",
#elif defined(OS_CYGWIN)
"$JAVA_HOME/jre/bin/classic/jvm.dll", /* Sun JDK 1.3 */
"$JAVA_HOME/jre/bin/client/jvm.dll", /* Sun JDK 1.4 */
#elif defined(OS_LINUX) || defined(OS_SOLARIS) || defined(OS_BSD) || defined(OS_SYSV) || defined(OS_FREEBSD) || defined(OS_TRU64) || defined(OS_AIX)
"$JAVA_HOME/jre/lib/" CPU "/classic/libjvm.so", /* Sun JDK 1.2 */
"$JAVA_HOME/jre/lib/" CPU "/server/libjvm.so", /* Sun JDK 1.4 */
"$JAVA_HOME/jre/lib/" CPU "/client/libjvm.so", /* Sun JDK 1.3 */
"$JAVA_HOME/jre/lib/" CPU "/libjvm.so", /* Sun JDK */
"$JAVA_HOME/lib/" CPU "/classic/libjvm.so", /* Sun JRE 1.2 */
"$JAVA_HOME/lib/" CPU "/server/libjvm.so", /* Sun JRE 1.4 */
"$JAVA_HOME/lib/" CPU "/client/libjvm.so", /* Sun JRE 1.3 */
"$JAVA_HOME/lib/" CPU "/libjvm.so", /* Sun JRE */
"$JAVA_HOME/jre/bin/" CPU "/classic/libjvm.so", /* IBM JDK 1.3 */
"$JAVA_HOME/jre/bin/" CPU "/libjvm.so", /* IBM JDK */
"$JAVA_HOME/bin/" CPU "/classic/libjvm.so", /* IBM JRE 1.3 */
"$JAVA_HOME/bin/" CPU "/libjvm.so", /* IBM JRE */
/* Those are "weirdos: if we got here, we're probably in troubles and
* we're not going to find anything, but hope never dies...
*/
"$JAVA_HOME/jre/lib/" CPU "/classic/green_threads/libjvm.so",
#if defined(OSD_POSIX)
"$JAVA_HOME/lib/s390/client/green_threads/libjvm.so",
"$JAVA_HOME/lib/sparc/client/green_threads/libjvm.so",
#endif
"$JAVA_HOME/jre/lib/classic/libjvm.so",
"$JAVA_HOME/jre/lib/client/libjvm.so",
"$JAVA_HOME/jre/lib/libjvm.so",
"$JAVA_HOME/lib/classic/libjvm.so",
"$JAVA_HOME/lib/client/libjvm.so",
"$JAVA_HOME/lib/libjvm.so",
"$JAVA_HOME/jre/bin/classic/libjvm.so",
"$JAVA_HOME/jre/bin/client/libjvm.so",
"$JAVA_HOME/jre/bin/libjvm.so",
"$JAVA_HOME/bin/classic/libjvm.so",
"$JAVA_HOME/bin/client/libjvm.so",
"$JAVA_HOME/bin/libjvm.so",
"$JAVA_HOME/jre/lib/" CPU "/fast64/libjvm.so",
"$JAVA_HOME/jre/lib/" CPU "/fast32/libjvm.so",
"$JAVA_HOME/lib/" CPU "/fast64/libjvm.so",
"$JAVA_HOME/lib/" CPU "/fast32/libjvm.so",
#elif defined(OS_HPUX)
"$JAVA_HOME/jre/lib/" CPU "/server/libjvm." SO_EXT,
"$JAVA_HOME/jre/lib/" CPU "/client/libjvm." SO_EXT,
"$JAVA_HOME/jre/lib/" CPU "/hotspot/libjvm." SO_EXT,
"$JAVA_HOME/jre/lib/" CPU "/classic/libjvm." SO_EXT,
#endif
"/usr/lib/libgcj.so.7", /* gcc java libraries */
"/usr/lib/libgcj.so.6",
NULL,
};
/* This is the list of "configured" VM (searched when jvm.cfg is found, as
* in the case of most JDKs 1.3 (not IBM, for example), way easier than
* before, and lovely, indeed...
*/
char *location_jvm_configured[] = {
#if defined(OS_DARWIN)
"$JAVA_HOME/lib/$VM_NAME/libjvm.dylib", /* Java 9 */
"$JAVA_HOME/jre/lib/$VM_NAME/libjvm.dylib",
"$JAVA_HOME/../Libraries/lib$VM_NAME.dylib",
#elif defined(OS_CYGWIN)
"$JAVA_HOME/jre/bin/$VM_NAME/jvm.dll", /* Sun JDK 1.3 */
#elif defined(OS_LINUX) || defined(OS_SOLARIS) || defined(OS_BSD) || defined(OS_FREEBSD) || defined(OS_TRU64) || defined(OS_AIX)
"$JAVA_HOME/lib/$VM_NAME/libjvm.so", /* Java 9 */
"$JAVA_HOME/jre/lib/" CPU "/$VM_NAME/libjvm.so", /* Sun JDK 1.3 */
"$JAVA_HOME/lib/" CPU "/$VM_NAME/libjvm.so", /* Sun JRE 1.3 */
#if defined(OS_AIX)
"$JAVA_HOME/jre/lib/ppc/$VM_NAME/libjvm.so", /* Sun JDK 1.3 */
"$JAVA_HOME/lib/ppc/$VM_NAME/libjvm.so", /* Sun JRE 1.3 */
#endif
#elif defined(OS_HPUX)
"$JAVA_HOME/jre/lib/" CPU "/$VM_NAME/libjvm." SO_EXT,
"$JAVA_HOME/lib/" CPU "/$VM_NAME/libjvm." SO_EXT,
#elif defined(OS_SYSV)
"$JAVA_HOME/jre/lib/" CPU "/$VM_NAME/dce_threads/libjvm.so",
"$JAVA_HOME/jre/lib/" CPU "/$VM_NAME/green_threads/libjvm.so",
"$JAVA_HOME/lib/" CPU "/$VM_NAME/dce_threads/libjvm.so",
"$JAVA_HOME/lib/" CPU "/$VM_NAME/green_threads/libjvm.so",
#endif
NULL,
};
/* 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.
*/
#ifndef __JSVC_LOCATION_H__
#define __JSVC_LOCATION_H__
#include "jsvc.h"
extern char *location_home[];
extern char *location_jvm_cfg[];
extern char *location_jvm_default[];
extern char *location_jvm_configured[];
#endif /* __JSVC_LOCATION_H__ */
/* 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.
*/
/*
* as Cygwin does not support lockf, jsvc uses fcntl to emulate it.
*/
#ifdef OS_CYGWIN
#include "jsvc.h"
#include <sys/fcntl.h>
/*
* File locking routine
*/
int lockf(int fildes, int function, off_t size)
{
struct flock buf;
switch (function) {
case F_LOCK:
buf.l_type = F_WRLCK;
break;
case F_ULOCK:
buf.l_type = F_UNLCK;
break;
default:
return -1;
}
buf.l_whence = 0;
buf.l_start = 0;
buf.l_len = size;
return fcntl(fildes, F_SETLK, &buf);
}
#else
const char __unused_locks_c[] = __FILE__;
#endif
/* 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.
*/
#ifndef __JSVC_LOCKS_H__
#define __JSVC_LOCKS_H__
/*
* as Cygwin does not support locks, jsvc use NT API to emulate them.
*/
#ifdef OS_CYGWIN
#define F_ULOCK 0 /* Unlock a previously locked region */
#define F_LOCK 1 /* Lock a region for exclusive use */
/*
* allow a file to be locked
* @param fildes an open file descriptor
* @param function a control value that specifies the action to be taken
* @param size number of bytes to lock
* @return Zero on success, a value less than 0 if an error was encountered
*/
int lockf(int fildes, int function, off_t size);
#endif
#endif /* __JSVC_LOCKS_H__ */
/* 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 "jsvc.h"
/* Replace all occurrences of a string in another */
int replace(char *new, int len, char *old, char *mch, char *rpl)
{
char *tmp;
int count;
int shift;
int nlen;
int olen;
int mlen;
int rlen;
int x;
/* The new buffer is NULL, fail */
if (new == NULL)
return -1;
/* The length of the buffer is less than zero, fail */
if (len < 0)
return -2;
/* The old buffer is NULL, fail */
if (old == NULL)
return -3;
/* The string to be matched is NULL or empty, simply copy */
if ((mch == NULL) || (strlen(mch) == 0)) {
olen = strlen(old);
if (len <= olen)
return (olen + 1);
strcpy(new, old);
return 0;
}
/* The string to be replaced is NULL, assume it's an empty string */
if (rpl == NULL)
rpl = "";
/* Evaluate some lengths */
olen = strlen(old);
mlen = strlen(mch);
rlen = strlen(rpl);
/* Calculate how many times the mch string appears in old */
tmp = old;
count = 0;
while ((tmp = strstr(tmp, mch)) != NULL) {
count++;
tmp += mlen;
}
/* We have no matches, simply copy */
if (count == 0) {
olen = strlen(old);
if (len <= olen)
return (olen + 1);
strcpy(new, old);
return 0;
}
/* Calculate how big the buffer must be to hold the translation
* and of how many bytes we need to shift the data
*/
shift = rlen - mlen;
nlen = olen + (shift * count);
/* printf("Count=%d Shift= %d OLen=%d NLen=%d\n",count,shift,olen,nlen); */
/* Check if we have enough size in the buffer */
if (nlen >= len)
return (nlen + 1);
/* Copy over the old buffer in the new one (save memory) */
strcpy(new, old);
/* Start replacing */
tmp = new;
while ((tmp = strstr(tmp, mch)) != NULL) {
/* If shift is > 0 we need to move data from right to left */
if (shift > 0) {
for (x = (strlen(tmp) + shift); x > shift; x--) {
/*
printf("src %c(%d) dst %c(%d)\n",
tmp[x-shift],tmp[x-shift],tmp[x],tmp[x]);
*/
tmp[x] = tmp[x - shift];
}
/* If shift is < 0 we need to move data from left to right */
}
else if (shift < 0) {
for (x = mlen; x < strlen(tmp) - shift; x++) {
/*
printf("src %c(%d) dst %c(%d)\n",
tmp[x],tmp[x],tmp[x+shift],tmp[x+shift]);
*/
tmp[x + shift] = tmp[x];
}
}
/* If shift is = 0 we don't have to shift data */
strncpy(tmp, rpl, rlen);
tmp += rlen;
/* printf("\"%s\"\n",tmp); */
}
return 0;
}
/* 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.
*/
#ifndef __JSVC_REPLACE_H__
#define __JSVC_REPLACE_H__
/**
* Replace all occurrences of mch in old with the new string rpl, and
* stores the result in new, provided that its length (specified in len)
* is enough.
*
* @param new The buffer where the result of the replace operation will be
* stored into.
* @param len The length of the previous buffer.
* @param old The string where occurrences of mtch must be searched.
* @param mch The characters to match in old (and to be replaced)
* @param rpl The characters that will be replaced in place of mch.
* @return Zero on success, a value less than 0 if an error was encountered
* or a value greater than zero (indicating the required storage size
* for new) if the buffer was too short to hold the new string.
*/
int replace(char *new, int len, char *old, char *mch, char *rpl);
#endif /* ifndef __JSVC_REPLACE_H__ */
/* 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.
*/
/*
* as Windows does not support signal, jsvc uses events to emulate them.
* The supported signal is SIGTERM.
* The kills.c contains the kill logic.
*/
#ifdef OS_CYGWIN
#include <windows.h>
#include <stdio.h>
static void (*HandleTerm) (void) = NULL; /* address of the handler routine. */
/*
* Event handling routine
*/
void v_difthf(LPVOID par)
{
HANDLE hevint; /* make a local copy because the parameter is shared! */
hevint = (HANDLE) par;
for (;;) {
if (WaitForSingleObject(hevint, INFINITE) == WAIT_FAILED) {
/* something have gone wrong. */
return; /* may be something more is needed. */
}
/* call the interrupt handler. */
if (HandleTerm == NULL)
return;
HandleTerm();
}
}
/*
* set a routine handler for the signal
* note that it cannot be used to change the signal handler
*/
int SetTerm(void (*func) (void))
{
char Name[256];
HANDLE hevint, hthread;
DWORD ThreadId;
SECURITY_ATTRIBUTES sa;
SECURITY_DESCRIPTOR sd;
sprintf(Name, "TERM%ld", GetCurrentProcessId());
/*
* event cannot be inherited.
* the event is reseted to nonsignaled after the waiting thread is released.
* the start state is resetted.
*/
/* Initialize the new security descriptor. */
InitializeSecurityDescriptor(&sd, SECURITY_DESCRIPTOR_REVISION);
/* Add a NULL descriptor ACL to the security descriptor. */
SetSecurityDescriptorDacl(&sd, TRUE, (PACL) NULL, FALSE);
sa.nLength = sizeof(sa);
sa.lpSecurityDescriptor = &sd;
sa.bInheritHandle = TRUE;
/* It works also with NULL instead &sa!! */
hevint = CreateEvent(&sa, FALSE, FALSE, Name);
HandleTerm = func;
if (hevint == NULL)
return -1; /* failed */
/* create the thread to wait for event */
hthread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) v_difthf,
(LPVOID) hevint, 0, &ThreadId);
if (hthread == NULL) {
/* failed remove the event */
CloseHandle(hevint); /* windows will remove it. */
return -1;
}
CloseHandle(hthread); /* not needed */
return 0;
}
#else
const char __unused_signals_c[] = __FILE__;
#endif
/*
Copyright 2001-2004 The Apache Software Foundation.
Licensed 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.
*/
#ifndef __JSVC_SIGNALS_H__
#define __JSVC_SIGNALS_H__
/*
* as Windows does not support signal, jsvc use event to emulate them.
* The supported signal is SIGTERM.
*/
#ifdef OS_CYGWIN
/*
* set a routine handler for the signal
* note that it cannot be used to change the signal handler
* @param func The function to call on termination
* @return Zero on success, a value less than 0 if an error was encountered
*/
int SetTerm(void (*func) (void));
#endif
#endif /* ifndef __JSVC_SIGNALS_H__ */
/* 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.
*/
#ifndef __VERSION_H__
#define __VERSION_H__
/**
* Major API changes that could cause compatibility problems for older
* programs such as structure size changes. No binary compatibility is
* possible across a change in the major version.
*/
#define JSVC_MAJOR_VERSION 1
/**
* Minor API changes that do not cause binary compatibility problems.
* Should be reset to 0 when upgrading JSVC_MAJOR_VERSION
*/
#define JSVC_MINOR_VERSION 1
/** patch level */
#define JSVC_PATCH_VERSION 0
/**
* This symbol is defined for internal, "development" copies of JSVC.
* This symbol will be #undef'd for releases.
*/
#define JSVC_IS_DEV_VERSION 0
/** Properly quote a value as a string in the C preprocessor */
#define JSVC_STRINGIFY(n) JSVC_STRINGIFY_HELPER(n)
/** Helper macro for JSVC_STRINGIFY */
#define JSVC_STRINGIFY_HELPER(n) #n
/** The formatted string of APU's version */
#define JSVC_VERSION_STRING \
JSVC_STRINGIFY(JSVC_MAJOR_VERSION) "." \
JSVC_STRINGIFY(JSVC_MINOR_VERSION) "." \
JSVC_STRINGIFY(JSVC_PATCH_VERSION) \
JSVC_IS_DEV_STRING
/** Internal: string form of the "is dev" flag */
#if JSVC_IS_DEV_VERSION
#define JSVC_IS_DEV_STRING "-dev"
#else
#define JSVC_IS_DEV_STRING ""
#endif
#endif /* __VERSION_H__ */
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册