Merge remote-tracking branch 'origin/vendor' into develop

This commit is contained in:
2013-07-30 14:46:45 +02:00
90 changed files with 0 additions and 23517 deletions

View File

@@ -1,246 +0,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.
*/
package org.apache.commons.logging;
/**
* <p>A simple logging interface abstracting logging APIs. In order to be
* instantiated successfully by {@link LogFactory}, classes that implement
* this interface must have a constructor that takes a single String
* parameter representing the "name" of this Log.</p>
*
* <p> The six logging levels used by <code>Log</code> are (in order):
* <ol>
* <li>trace (the least serious)</li>
* <li>debug</li>
* <li>info</li>
* <li>warn</li>
* <li>error</li>
* <li>fatal (the most serious)</li>
* </ol>
* The mapping of these log levels to the concepts used by the underlying
* logging system is implementation dependent.
* The implemention should ensure, though, that this ordering behaves
* as expected.</p>
*
* <p>Performance is often a logging concern.
* By examining the appropriate property,
* a component can avoid expensive operations (producing information
* to be logged).</p>
*
* <p> For example,
* <code><pre>
* if (log.isDebugEnabled()) {
* ... do something expensive ...
* log.debug(theResult);
* }
* </pre></code>
* </p>
*
* <p>Configuration of the underlying logging system will generally be done
* external to the Logging APIs, through whatever mechanism is supported by
* that system.</p>
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
* @version $Id: Log.java 424107 2006-07-20 23:15:42Z skitching $
*/
public interface Log {
// ----------------------------------------------------- Logging Properties
/**
* <p> Is debug logging currently enabled? </p>
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
* when the log level is more than debug. </p>
*
* @return true if debug is enabled in the underlying logger.
*/
public boolean isDebugEnabled();
/**
* <p> Is error logging currently enabled? </p>
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
* when the log level is more than error. </p>
*
* @return true if error is enabled in the underlying logger.
*/
public boolean isErrorEnabled();
/**
* <p> Is fatal logging currently enabled? </p>
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
* when the log level is more than fatal. </p>
*
* @return true if fatal is enabled in the underlying logger.
*/
public boolean isFatalEnabled();
/**
* <p> Is info logging currently enabled? </p>
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
* when the log level is more than info. </p>
*
* @return true if info is enabled in the underlying logger.
*/
public boolean isInfoEnabled();
/**
* <p> Is trace logging currently enabled? </p>
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
* when the log level is more than trace. </p>
*
* @return true if trace is enabled in the underlying logger.
*/
public boolean isTraceEnabled();
/**
* <p> Is warn logging currently enabled? </p>
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
* when the log level is more than warn. </p>
*
* @return true if warn is enabled in the underlying logger.
*/
public boolean isWarnEnabled();
// -------------------------------------------------------- Logging Methods
/**
* <p> Log a message with trace log level. </p>
*
* @param message log this message
*/
public void trace(Object message);
/**
* <p> Log an error with trace log level. </p>
*
* @param message log this message
* @param t log this cause
*/
public void trace(Object message, Throwable t);
/**
* <p> Log a message with debug log level. </p>
*
* @param message log this message
*/
public void debug(Object message);
/**
* <p> Log an error with debug log level. </p>
*
* @param message log this message
* @param t log this cause
*/
public void debug(Object message, Throwable t);
/**
* <p> Log a message with info log level. </p>
*
* @param message log this message
*/
public void info(Object message);
/**
* <p> Log an error with info log level. </p>
*
* @param message log this message
* @param t log this cause
*/
public void info(Object message, Throwable t);
/**
* <p> Log a message with warn log level. </p>
*
* @param message log this message
*/
public void warn(Object message);
/**
* <p> Log an error with warn log level. </p>
*
* @param message log this message
* @param t log this cause
*/
public void warn(Object message, Throwable t);
/**
* <p> Log a message with error log level. </p>
*
* @param message log this message
*/
public void error(Object message);
/**
* <p> Log an error with error log level. </p>
*
* @param message log this message
* @param t log this cause
*/
public void error(Object message, Throwable t);
/**
* <p> Log a message with fatal log level. </p>
*
* @param message log this message
*/
public void fatal(Object message);
/**
* <p> Log an error with fatal log level. </p>
*
* @param message log this message
* @param t log this cause
*/
public void fatal(Object message, Throwable t);
}

View File

@@ -1,98 +0,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.
*/
package org.apache.commons.logging;
/**
* <p>An exception that is thrown only if a suitable <code>LogFactory</code>
* or <code>Log</code> instance cannot be created by the corresponding
* factory methods.</p>
*
* @author Craig R. McClanahan
* @version $Revision: 424107 $ $Date: 2006-07-21 01:15:42 +0200 (fr, 21 jul 2006) $
*/
public class LogConfigurationException extends RuntimeException {
/**
* Construct a new exception with <code>null</code> as its detail message.
*/
public LogConfigurationException() {
super();
}
/**
* Construct a new exception with the specified detail message.
*
* @param message The detail message
*/
public LogConfigurationException(String message) {
super(message);
}
/**
* Construct a new exception with the specified cause and a derived
* detail message.
*
* @param cause The underlying cause
*/
public LogConfigurationException(Throwable cause) {
this((cause == null) ? null : cause.toString(), cause);
}
/**
* Construct a new exception with the specified detail message and cause.
*
* @param message The detail message
* @param cause The underlying cause
*/
public LogConfigurationException(String message, Throwable cause) {
super(message + " (Caused by " + cause + ")");
this.cause = cause; // Two-argument version requires JDK 1.4 or later
}
/**
* The underlying cause of this exception.
*/
protected Throwable cause = null;
/**
* Return the underlying cause of this exception (if any).
*/
public Throwable getCause() {
return (this.cause);
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -1,262 +0,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.
*/
package org.apache.commons.logging;
import java.lang.reflect.Constructor;
import java.util.Hashtable;
import org.apache.commons.logging.impl.NoOpLog;
/**
* <p>Factory for creating {@link Log} instances. Applications should call
* the <code>makeNewLogInstance()</code> method to instantiate new instances
* of the configured {@link Log} implementation class.</p>
*
* <p>By default, calling <code>getInstance()</code> will use the following
* algorithm:</p>
* <ul>
* <li>If Log4J is available, return an instance of
* <code>org.apache.commons.logging.impl.Log4JLogger</code>.</li>
* <li>If JDK 1.4 or later is available, return an instance of
* <code>org.apache.commons.logging.impl.Jdk14Logger</code>.</li>
* <li>Otherwise, return an instance of
* <code>org.apache.commons.logging.impl.NoOpLog</code>.</li>
* </ul>
*
* <p>You can change the default behavior in one of two ways:</p>
* <ul>
* <li>On the startup command line, set the system property
* <code>org.apache.commons.logging.log</code> to the name of the
* <code>org.apache.commons.logging.Log</code> implementation class
* you want to use.</li>
* <li>At runtime, call <code>LogSource.setLogImplementation()</code>.</li>
* </ul>
*
* @deprecated Use {@link LogFactory} instead - The default factory
* implementation performs exactly the same algorithm as this class did
*
* @author Rod Waldhoff
* @version $Id: LogSource.java 424107 2006-07-20 23:15:42Z skitching $
*/
public class LogSource {
// ------------------------------------------------------- Class Attributes
static protected Hashtable logs = new Hashtable();
/** Is log4j available (in the current classpath) */
static protected boolean log4jIsAvailable = false;
/** Is JDK 1.4 logging available */
static protected boolean jdk14IsAvailable = false;
/** Constructor for current log class */
static protected Constructor logImplctor = null;
// ----------------------------------------------------- Class Initializers
static {
// Is Log4J Available?
try {
if (null != Class.forName("org.apache.log4j.Logger")) {
log4jIsAvailable = true;
} else {
log4jIsAvailable = false;
}
} catch (Throwable t) {
log4jIsAvailable = false;
}
// Is JDK 1.4 Logging Available?
try {
if ((null != Class.forName("java.util.logging.Logger")) &&
(null != Class.forName("org.apache.commons.logging.impl.Jdk14Logger"))) {
jdk14IsAvailable = true;
} else {
jdk14IsAvailable = false;
}
} catch (Throwable t) {
jdk14IsAvailable = false;
}
// Set the default Log implementation
String name = null;
try {
name = System.getProperty("org.apache.commons.logging.log");
if (name == null) {
name = System.getProperty("org.apache.commons.logging.Log");
}
} catch (Throwable t) {
}
if (name != null) {
try {
setLogImplementation(name);
} catch (Throwable t) {
try {
setLogImplementation
("org.apache.commons.logging.impl.NoOpLog");
} catch (Throwable u) {
;
}
}
} else {
try {
if (log4jIsAvailable) {
setLogImplementation
("org.apache.commons.logging.impl.Log4JLogger");
} else if (jdk14IsAvailable) {
setLogImplementation
("org.apache.commons.logging.impl.Jdk14Logger");
} else {
setLogImplementation
("org.apache.commons.logging.impl.NoOpLog");
}
} catch (Throwable t) {
try {
setLogImplementation
("org.apache.commons.logging.impl.NoOpLog");
} catch (Throwable u) {
;
}
}
}
}
// ------------------------------------------------------------ Constructor
/** Don't allow others to create instances */
private LogSource() {
}
// ---------------------------------------------------------- Class Methods
/**
* Set the log implementation/log implementation factory
* by the name of the class. The given class
* must implement {@link Log}, and provide a constructor that
* takes a single {@link String} argument (containing the name
* of the log).
*/
static public void setLogImplementation(String classname) throws
LinkageError, ExceptionInInitializerError,
NoSuchMethodException, SecurityException,
ClassNotFoundException {
try {
Class logclass = Class.forName(classname);
Class[] argtypes = new Class[1];
argtypes[0] = "".getClass();
logImplctor = logclass.getConstructor(argtypes);
} catch (Throwable t) {
logImplctor = null;
}
}
/**
* Set the log implementation/log implementation factory
* by class. The given class must implement {@link Log},
* and provide a constructor that takes a single {@link String}
* argument (containing the name of the log).
*/
static public void setLogImplementation(Class logclass) throws
LinkageError, ExceptionInInitializerError,
NoSuchMethodException, SecurityException {
Class[] argtypes = new Class[1];
argtypes[0] = "".getClass();
logImplctor = logclass.getConstructor(argtypes);
}
/** Get a <code>Log</code> instance by class name */
static public Log getInstance(String name) {
Log log = (Log) (logs.get(name));
if (null == log) {
log = makeNewLogInstance(name);
logs.put(name, log);
}
return log;
}
/** Get a <code>Log</code> instance by class */
static public Log getInstance(Class clazz) {
return getInstance(clazz.getName());
}
/**
* Create a new {@link Log} implementation, based
* on the given <i>name</i>.
* <p>
* The specific {@link Log} implementation returned
* is determined by the value of the
* <tt>org.apache.commons.logging.log</tt> property.
* The value of <tt>org.apache.commons.logging.log</tt> may be set to
* the fully specified name of a class that implements
* the {@link Log} interface. This class must also
* have a public constructor that takes a single
* {@link String} argument (containing the <i>name</i>
* of the {@link Log} to be constructed.
* <p>
* When <tt>org.apache.commons.logging.log</tt> is not set,
* or when no corresponding class can be found,
* this method will return a Log4JLogger
* if the log4j Logger class is
* available in the {@link LogSource}'s classpath, or a
* Jdk14Logger if we are on a JDK 1.4 or later system, or
* NoOpLog if neither of the above conditions is true.
*
* @param name the log name (or category)
*/
static public Log makeNewLogInstance(String name) {
Log log = null;
try {
Object[] args = new Object[1];
args[0] = name;
log = (Log) (logImplctor.newInstance(args));
} catch (Throwable t) {
log = null;
}
if (null == log) {
log = new NoOpLog(name);
}
return log;
}
/**
* Returns a {@link String} array containing the names of
* all logs known to me.
*/
static public String[] getLogNames() {
return (String[]) (logs.keySet().toArray(new String[logs.size()]));
}
}

View File

@@ -1,292 +0,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.
*/
package org.apache.commons.logging.impl;
import org.apache.avalon.framework.logger.Logger;
import org.apache.commons.logging.Log;
/**
* <p>Implementation of commons-logging Log interface that delegates all
* logging calls to the Avalon logging abstraction: the Logger interface.
* </p>
* <p>
* There are two ways in which this class can be used:
* </p>
* <ul>
* <li>the instance can be constructed with an Avalon logger
* (by calling {@link #AvalonLogger(Logger)}). In this case, it acts
* as a simple thin wrapping implementation over the logger. This is
* particularly useful when using a property setter.
* </li>
* <li>the {@link #setDefaultLogger} class property can be called which
* sets the ancesteral Avalon logger for this class. Any <code>AvalonLogger</code>
* instances created through the <code>LogFactory</code> mechanisms will output
* to child loggers of this <code>Logger</code>.
* </li>
* </ul>
* <p>
* <strong>Note:</strong> <code>AvalonLogger</code> does not implement Serializable
* because the constructors available for it make this impossible to achieve in all
* circumstances; there is no way to "reconnect" to an underlying Logger object on
* deserialization if one was just passed in to the constructor of the original
* object. This class <i>was</i> marked Serializable in the 1.0.4 release of
* commons-logging, but this never actually worked (a NullPointerException would
* be thrown as soon as the deserialized object was used), so removing this marker
* is not considered to be an incompatible change.
* </p>
* @author <a href="mailto:neeme@apache.org">Neeme Praks</a>
* @version $Revision: 424107 $ $Date: 2006-07-21 01:15:42 +0200 (fr, 21 jul 2006) $
*/
public class AvalonLogger implements Log {
/** Ancesteral avalon logger */
private static Logger defaultLogger = null;
/** Avalon logger used to perform log */
private transient Logger logger = null;
/**
* Constructs an <code>AvalonLogger</code> that outputs to the given
* <code>Logger</code> instance.
* @param logger the avalon logger implementation to delegate to
*/
public AvalonLogger(Logger logger) {
this.logger = logger;
}
/**
* Constructs an <code>AvalonLogger</code> that will log to a child
* of the <code>Logger</code> set by calling {@link #setDefaultLogger}.
* @param name the name of the avalon logger implementation to delegate to
*/
public AvalonLogger(String name) {
if (defaultLogger == null)
throw new NullPointerException("default logger has to be specified if this constructor is used!");
this.logger = defaultLogger.getChildLogger(name);
}
/**
* Gets the Avalon logger implementation used to perform logging.
* @return avalon logger implementation
*/
public Logger getLogger() {
return logger;
}
/**
* Sets the ancesteral Avalon logger from which the delegating loggers
* will descend.
* @param logger the default avalon logger,
* in case there is no logger instance supplied in constructor
*/
public static void setDefaultLogger(Logger logger) {
defaultLogger = logger;
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.debug</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#debug(Object, Throwable)
*/
public void debug(Object message, Throwable t) {
if (getLogger().isDebugEnabled()) getLogger().debug(String.valueOf(message), t);
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.debug</code>.
*
* @param message to log.
* @see org.apache.commons.logging.Log#debug(Object)
*/
public void debug(Object message) {
if (getLogger().isDebugEnabled()) getLogger().debug(String.valueOf(message));
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.error</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#error(Object, Throwable)
*/
public void error(Object message, Throwable t) {
if (getLogger().isErrorEnabled()) getLogger().error(String.valueOf(message), t);
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.error</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#error(Object)
*/
public void error(Object message) {
if (getLogger().isErrorEnabled()) getLogger().error(String.valueOf(message));
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.fatalError</code>.
*
* @param message to log.
* @param t log this cause.
* @see org.apache.commons.logging.Log#fatal(Object, Throwable)
*/
public void fatal(Object message, Throwable t) {
if (getLogger().isFatalErrorEnabled()) getLogger().fatalError(String.valueOf(message), t);
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.fatalError</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#fatal(Object)
*/
public void fatal(Object message) {
if (getLogger().isFatalErrorEnabled()) getLogger().fatalError(String.valueOf(message));
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.info</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#info(Object, Throwable)
*/
public void info(Object message, Throwable t) {
if (getLogger().isInfoEnabled()) getLogger().info(String.valueOf(message), t);
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.info</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#info(Object)
*/
public void info(Object message) {
if (getLogger().isInfoEnabled()) getLogger().info(String.valueOf(message));
}
/**
* Is logging to
* <code>org.apache.avalon.framework.logger.Logger.debug</code> enabled?
* @see org.apache.commons.logging.Log#isDebugEnabled()
*/
public boolean isDebugEnabled() {
return getLogger().isDebugEnabled();
}
/**
* Is logging to
* <code>org.apache.avalon.framework.logger.Logger.error</code> enabled?
* @see org.apache.commons.logging.Log#isErrorEnabled()
*/
public boolean isErrorEnabled() {
return getLogger().isErrorEnabled();
}
/**
* Is logging to
* <code>org.apache.avalon.framework.logger.Logger.fatalError</code> enabled?
* @see org.apache.commons.logging.Log#isFatalEnabled()
*/
public boolean isFatalEnabled() {
return getLogger().isFatalErrorEnabled();
}
/**
* Is logging to
* <code>org.apache.avalon.framework.logger.Logger.info</code> enabled?
* @see org.apache.commons.logging.Log#isInfoEnabled()
*/
public boolean isInfoEnabled() {
return getLogger().isInfoEnabled();
}
/**
* Is logging to
* <code>org.apache.avalon.framework.logger.Logger.debug</code> enabled?
* @see org.apache.commons.logging.Log#isTraceEnabled()
*/
public boolean isTraceEnabled() {
return getLogger().isDebugEnabled();
}
/**
* Is logging to
* <code>org.apache.avalon.framework.logger.Logger.warn</code> enabled?
* @see org.apache.commons.logging.Log#isWarnEnabled()
*/
public boolean isWarnEnabled() {
return getLogger().isWarnEnabled();
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.debug</code>.
*
* @param message to log.
* @param t log this cause.
* @see org.apache.commons.logging.Log#trace(Object, Throwable)
*/
public void trace(Object message, Throwable t) {
if (getLogger().isDebugEnabled()) getLogger().debug(String.valueOf(message), t);
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.debug</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#trace(Object)
*/
public void trace(Object message) {
if (getLogger().isDebugEnabled()) getLogger().debug(String.valueOf(message));
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.warn</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#warn(Object, Throwable)
*/
public void warn(Object message, Throwable t) {
if (getLogger().isWarnEnabled()) getLogger().warn(String.valueOf(message), t);
}
/**
* Logs a message with
* <code>org.apache.avalon.framework.logger.Logger.warn</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#warn(Object)
*/
public void warn(Object message) {
if (getLogger().isWarnEnabled()) getLogger().warn(String.valueOf(message));
}
}

View File

@@ -1,335 +0,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.
*/
package org.apache.commons.logging.impl;
import java.io.Serializable;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.logging.LogRecord;
import java.util.StringTokenizer;
import java.io.PrintWriter;
import java.io.StringWriter;
import org.apache.commons.logging.Log;
/**
* <p>Implementation of the <code>org.apache.commons.logging.Log</code>
* interface that wraps the standard JDK logging mechanisms that are
* available in SourceForge's Lumberjack for JDKs prior to 1.4.</p>
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author <a href="mailto:bloritsch@apache.org">Berin Loritsch</a>
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a>
* @author <a href="mailto:vince256@comcast.net">Vince Eagen</a>
* @version $Revision: 424107 $ $Date: 2006-07-21 01:15:42 +0200 (fr, 21 jul 2006) $
* @since 1.1
*/
public class Jdk13LumberjackLogger implements Log, Serializable {
// ----------------------------------------------------- Instance Variables
/**
* The underlying Logger implementation we are using.
*/
protected transient Logger logger = null;
protected String name = null;
private String sourceClassName = "unknown";
private String sourceMethodName = "unknown";
private boolean classAndMethodFound = false;
/**
* This member variable simply ensures that any attempt to initialise
* this class in a pre-1.4 JVM will result in an ExceptionInInitializerError.
* It must not be private, as an optimising compiler could detect that it
* is not used and optimise it away.
*/
protected static final Level dummyLevel = Level.FINE;
// ----------------------------------------------------------- Constructors
/**
* Construct a named instance of this Logger.
*
* @param name Name of the logger to be constructed
*/
public Jdk13LumberjackLogger(String name) {
this.name = name;
logger = getLogger();
}
// --------------------------------------------------------- Public Methods
private void log( Level level, String msg, Throwable ex ) {
if( getLogger().isLoggable(level) ) {
LogRecord record = new LogRecord(level, msg);
if( !classAndMethodFound ) {
getClassAndMethod();
}
record.setSourceClassName(sourceClassName);
record.setSourceMethodName(sourceMethodName);
if( ex != null ) {
record.setThrown(ex);
}
getLogger().log(record);
}
}
/**
* <p>Gets the class and method by looking at the stack trace for the
* first entry that is not this class.</p>
*/
private void getClassAndMethod() {
try {
Throwable throwable = new Throwable();
throwable.fillInStackTrace();
StringWriter stringWriter = new StringWriter();
PrintWriter printWriter = new PrintWriter( stringWriter );
throwable.printStackTrace( printWriter );
String traceString = stringWriter.getBuffer().toString();
StringTokenizer tokenizer =
new StringTokenizer( traceString, "\n" );
tokenizer.nextToken();
String line = tokenizer.nextToken();
while ( line.indexOf( this.getClass().getName() ) == -1 ) {
line = tokenizer.nextToken();
}
while ( line.indexOf( this.getClass().getName() ) >= 0 ) {
line = tokenizer.nextToken();
}
int start = line.indexOf( "at " ) + 3;
int end = line.indexOf( '(' );
String temp = line.substring( start, end );
int lastPeriod = temp.lastIndexOf( '.' );
sourceClassName = temp.substring( 0, lastPeriod );
sourceMethodName = temp.substring( lastPeriod + 1 );
} catch ( Exception ex ) {
// ignore - leave class and methodname unknown
}
classAndMethodFound = true;
}
/**
* Logs a message with <code>java.util.logging.Level.FINE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#debug(Object)
*/
public void debug(Object message) {
log(Level.FINE, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.FINE</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#debug(Object, Throwable)
*/
public void debug(Object message, Throwable exception) {
log(Level.FINE, String.valueOf(message), exception);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#error(Object)
*/
public void error(Object message) {
log(Level.SEVERE, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#error(Object, Throwable)
*/
public void error(Object message, Throwable exception) {
log(Level.SEVERE, String.valueOf(message), exception);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#fatal(Object)
*/
public void fatal(Object message) {
log(Level.SEVERE, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#fatal(Object, Throwable)
*/
public void fatal(Object message, Throwable exception) {
log(Level.SEVERE, String.valueOf(message), exception);
}
/**
* Return the native Logger instance we are using.
*/
public Logger getLogger() {
if (logger == null) {
logger = Logger.getLogger(name);
}
return (logger);
}
/**
* Logs a message with <code>java.util.logging.Level.INFO</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#info(Object)
*/
public void info(Object message) {
log(Level.INFO, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.INFO</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#info(Object, Throwable)
*/
public void info(Object message, Throwable exception) {
log(Level.INFO, String.valueOf(message), exception);
}
/**
* Is debug logging currently enabled?
*/
public boolean isDebugEnabled() {
return (getLogger().isLoggable(Level.FINE));
}
/**
* Is error logging currently enabled?
*/
public boolean isErrorEnabled() {
return (getLogger().isLoggable(Level.SEVERE));
}
/**
* Is fatal logging currently enabled?
*/
public boolean isFatalEnabled() {
return (getLogger().isLoggable(Level.SEVERE));
}
/**
* Is info logging currently enabled?
*/
public boolean isInfoEnabled() {
return (getLogger().isLoggable(Level.INFO));
}
/**
* Is trace logging currently enabled?
*/
public boolean isTraceEnabled() {
return (getLogger().isLoggable(Level.FINEST));
}
/**
* Is warn logging currently enabled?
*/
public boolean isWarnEnabled() {
return (getLogger().isLoggable(Level.WARNING));
}
/**
* Logs a message with <code>java.util.logging.Level.FINEST</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#trace(Object)
*/
public void trace(Object message) {
log(Level.FINEST, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.FINEST</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#trace(Object, Throwable)
*/
public void trace(Object message, Throwable exception) {
log(Level.FINEST, String.valueOf(message), exception);
}
/**
* Logs a message with <code>java.util.logging.Level.WARNING</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#warn(Object)
*/
public void warn(Object message) {
log(Level.WARNING, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.WARNING</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#warn(Object, Throwable)
*/
public void warn(Object message, Throwable exception) {
log(Level.WARNING, String.valueOf(message), exception);
}
}

View File

@@ -1,304 +0,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.
*/
package org.apache.commons.logging.impl;
import java.io.Serializable;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.apache.commons.logging.Log;
/**
* <p>Implementation of the <code>org.apache.commons.logging.Log</code>
* interface that wraps the standard JDK logging mechanisms that were
* introduced in the Merlin release (JDK 1.4).</p>
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author <a href="mailto:bloritsch@apache.org">Berin Loritsch</a>
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a>
* @version $Revision: 424107 $ $Date: 2006-07-21 01:15:42 +0200 (fr, 21 jul 2006) $
*/
public class Jdk14Logger implements Log, Serializable {
/**
* This member variable simply ensures that any attempt to initialise
* this class in a pre-1.4 JVM will result in an ExceptionInInitializerError.
* It must not be private, as an optimising compiler could detect that it
* is not used and optimise it away.
*/
protected static final Level dummyLevel = Level.FINE;
// ----------------------------------------------------------- Constructors
/**
* Construct a named instance of this Logger.
*
* @param name Name of the logger to be constructed
*/
public Jdk14Logger(String name) {
this.name = name;
logger = getLogger();
}
// ----------------------------------------------------- Instance Variables
/**
* The underlying Logger implementation we are using.
*/
protected transient Logger logger = null;
/**
* The name of the logger we are wrapping.
*/
protected String name = null;
// --------------------------------------------------------- Public Methods
private void log( Level level, String msg, Throwable ex ) {
Logger logger = getLogger();
if (logger.isLoggable(level)) {
// Hack (?) to get the stack trace.
Throwable dummyException=new Throwable();
StackTraceElement locations[]=dummyException.getStackTrace();
// Caller will be the third element
String cname="unknown";
String method="unknown";
if( locations!=null && locations.length >2 ) {
StackTraceElement caller=locations[2];
cname=caller.getClassName();
method=caller.getMethodName();
}
if( ex==null ) {
logger.logp( level, cname, method, msg );
} else {
logger.logp( level, cname, method, msg, ex );
}
}
}
/**
* Logs a message with <code>java.util.logging.Level.FINE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#debug(Object)
*/
public void debug(Object message) {
log(Level.FINE, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.FINE</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#debug(Object, Throwable)
*/
public void debug(Object message, Throwable exception) {
log(Level.FINE, String.valueOf(message), exception);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#error(Object)
*/
public void error(Object message) {
log(Level.SEVERE, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#error(Object, Throwable)
*/
public void error(Object message, Throwable exception) {
log(Level.SEVERE, String.valueOf(message), exception);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#fatal(Object)
*/
public void fatal(Object message) {
log(Level.SEVERE, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.SEVERE</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#fatal(Object, Throwable)
*/
public void fatal(Object message, Throwable exception) {
log(Level.SEVERE, String.valueOf(message), exception);
}
/**
* Return the native Logger instance we are using.
*/
public Logger getLogger() {
if (logger == null) {
logger = Logger.getLogger(name);
}
return (logger);
}
/**
* Logs a message with <code>java.util.logging.Level.INFO</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#info(Object)
*/
public void info(Object message) {
log(Level.INFO, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.INFO</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#info(Object, Throwable)
*/
public void info(Object message, Throwable exception) {
log(Level.INFO, String.valueOf(message), exception);
}
/**
* Is debug logging currently enabled?
*/
public boolean isDebugEnabled() {
return (getLogger().isLoggable(Level.FINE));
}
/**
* Is error logging currently enabled?
*/
public boolean isErrorEnabled() {
return (getLogger().isLoggable(Level.SEVERE));
}
/**
* Is fatal logging currently enabled?
*/
public boolean isFatalEnabled() {
return (getLogger().isLoggable(Level.SEVERE));
}
/**
* Is info logging currently enabled?
*/
public boolean isInfoEnabled() {
return (getLogger().isLoggable(Level.INFO));
}
/**
* Is trace logging currently enabled?
*/
public boolean isTraceEnabled() {
return (getLogger().isLoggable(Level.FINEST));
}
/**
* Is warn logging currently enabled?
*/
public boolean isWarnEnabled() {
return (getLogger().isLoggable(Level.WARNING));
}
/**
* Logs a message with <code>java.util.logging.Level.FINEST</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#trace(Object)
*/
public void trace(Object message) {
log(Level.FINEST, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.FINEST</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#trace(Object, Throwable)
*/
public void trace(Object message, Throwable exception) {
log(Level.FINEST, String.valueOf(message), exception);
}
/**
* Logs a message with <code>java.util.logging.Level.WARNING</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#warn(Object)
*/
public void warn(Object message) {
log(Level.WARNING, String.valueOf(message), null);
}
/**
* Logs a message with <code>java.util.logging.Level.WARNING</code>.
*
* @param message to log
* @param exception log this cause
* @see org.apache.commons.logging.Log#warn(Object, Throwable)
*/
public void warn(Object message, Throwable exception) {
log(Level.WARNING, String.valueOf(message), exception);
}
}

View File

@@ -1,342 +0,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.
*/
package org.apache.commons.logging.impl;
import java.io.Serializable;
import org.apache.commons.logging.Log;
import org.apache.log4j.Logger;
import org.apache.log4j.Priority;
import org.apache.log4j.Level;
/**
* Implementation of {@link Log} that maps directly to a
* <strong>Logger</strong> for log4J version 1.2.
* <p>
* Initial configuration of the corresponding Logger instances should be done
* in the usual manner, as outlined in the Log4J documentation.
* <p>
* The reason this logger is distinct from the 1.3 logger is that in version 1.2
* of Log4J:
* <ul>
* <li>class Logger takes Priority parameters not Level parameters.
* <li>class Level extends Priority
* </ul>
* Log4J1.3 is expected to change Level so it no longer extends Priority, which is
* a non-binary-compatible change. The class generated by compiling this code against
* log4j 1.2 will therefore not run against log4j 1.3.
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
* @author Robert Burrell Donkin
* @version $Id: Log4JLogger.java 479747 2006-11-27 20:15:01Z dennisl $
*/
public class Log4JLogger implements Log, Serializable {
// ------------------------------------------------------------- Attributes
/** The fully qualified name of the Log4JLogger class. */
private static final String FQCN = Log4JLogger.class.getName();
/** Log to this logger */
private transient Logger logger = null;
/** Logger name */
private String name = null;
private static Priority traceLevel;
// ------------------------------------------------------------
// Static Initializer.
//
// Note that this must come after the static variable declarations
// otherwise initialiser expressions associated with those variables
// will override any settings done here.
//
// Verify that log4j is available, and that it is version 1.2.
// If an ExceptionInInitializerError is generated, then LogFactoryImpl
// will treat that as meaning that the appropriate underlying logging
// library is just not present - if discovery is in progress then
// discovery will continue.
// ------------------------------------------------------------
static {
if (!Priority.class.isAssignableFrom(Level.class)) {
// nope, this is log4j 1.3, so force an ExceptionInInitializerError
throw new InstantiationError("Log4J 1.2 not available");
}
// Releases of log4j1.2 >= 1.2.12 have Priority.TRACE available, earlier
// versions do not. If TRACE is not available, then we have to map
// calls to Log.trace(...) onto the DEBUG level.
try {
traceLevel = (Priority) Level.class.getDeclaredField("TRACE").get(null);
} catch(Exception ex) {
// ok, trace not available
traceLevel = Priority.DEBUG;
}
}
// ------------------------------------------------------------ Constructor
public Log4JLogger() {
}
/**
* Base constructor.
*/
public Log4JLogger(String name) {
this.name = name;
this.logger = getLogger();
}
/**
* For use with a log4j factory.
*/
public Log4JLogger(Logger logger ) {
if (logger == null) {
throw new IllegalArgumentException(
"Warning - null logger in constructor; possible log4j misconfiguration.");
}
this.name = logger.getName();
this.logger=logger;
}
// ---------------------------------------------------------
// Implementation
//
// Note that in the methods below the Priority class is used to define
// levels even though the Level class is supported in 1.2. This is done
// so that at compile time the call definitely resolves to a call to
// a method that takes a Priority rather than one that takes a Level.
//
// The Category class (and hence its subclass Logger) in version 1.2 only
// has methods that take Priority objects. The Category class (and hence
// Logger class) in version 1.3 has methods that take both Priority and
// Level objects. This means that if we use Level here, and compile
// against log4j 1.3 then calls would be bound to the versions of
// methods taking Level objects and then would fail to run against
// version 1.2 of log4j.
// ---------------------------------------------------------
/**
* Logs a message with <code>org.apache.log4j.Priority.TRACE</code>.
* When using a log4j version that does not support the <code>TRACE</code>
* level, the message will be logged at the <code>DEBUG</code> level.
*
* @param message to log
* @see org.apache.commons.logging.Log#trace(Object)
*/
public void trace(Object message) {
getLogger().log(FQCN, traceLevel, message, null );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.TRACE</code>.
* When using a log4j version that does not support the <code>TRACE</code>
* level, the message will be logged at the <code>DEBUG</code> level.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#trace(Object, Throwable)
*/
public void trace(Object message, Throwable t) {
getLogger().log(FQCN, traceLevel, message, t );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.DEBUG</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#debug(Object)
*/
public void debug(Object message) {
getLogger().log(FQCN, Priority.DEBUG, message, null );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.DEBUG</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#debug(Object, Throwable)
*/
public void debug(Object message, Throwable t) {
getLogger().log(FQCN, Priority.DEBUG, message, t );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.INFO</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#info(Object)
*/
public void info(Object message) {
getLogger().log(FQCN, Priority.INFO, message, null );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.INFO</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#info(Object, Throwable)
*/
public void info(Object message, Throwable t) {
getLogger().log(FQCN, Priority.INFO, message, t );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.WARN</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#warn(Object)
*/
public void warn(Object message) {
getLogger().log(FQCN, Priority.WARN, message, null );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.WARN</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#warn(Object, Throwable)
*/
public void warn(Object message, Throwable t) {
getLogger().log(FQCN, Priority.WARN, message, t );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.ERROR</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#error(Object)
*/
public void error(Object message) {
getLogger().log(FQCN, Priority.ERROR, message, null );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.ERROR</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#error(Object, Throwable)
*/
public void error(Object message, Throwable t) {
getLogger().log(FQCN, Priority.ERROR, message, t );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.FATAL</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#fatal(Object)
*/
public void fatal(Object message) {
getLogger().log(FQCN, Priority.FATAL, message, null );
}
/**
* Logs a message with <code>org.apache.log4j.Priority.FATAL</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#fatal(Object, Throwable)
*/
public void fatal(Object message, Throwable t) {
getLogger().log(FQCN, Priority.FATAL, message, t );
}
/**
* Return the native Logger instance we are using.
*/
public Logger getLogger() {
if (logger == null) {
logger = Logger.getLogger(name);
}
return (this.logger);
}
/**
* Check whether the Log4j Logger used is enabled for <code>DEBUG</code> priority.
*/
public boolean isDebugEnabled() {
return getLogger().isDebugEnabled();
}
/**
* Check whether the Log4j Logger used is enabled for <code>ERROR</code> priority.
*/
public boolean isErrorEnabled() {
return getLogger().isEnabledFor(Priority.ERROR);
}
/**
* Check whether the Log4j Logger used is enabled for <code>FATAL</code> priority.
*/
public boolean isFatalEnabled() {
return getLogger().isEnabledFor(Priority.FATAL);
}
/**
* Check whether the Log4j Logger used is enabled for <code>INFO</code> priority.
*/
public boolean isInfoEnabled() {
return getLogger().isInfoEnabled();
}
/**
* Check whether the Log4j Logger used is enabled for <code>TRACE</code> priority.
* When using a log4j version that does not support the TRACE level, this call
* will report whether <code>DEBUG</code> is enabled or not.
*/
public boolean isTraceEnabled() {
return getLogger().isEnabledFor(traceLevel);
}
/**
* Check whether the Log4j Logger used is enabled for <code>WARN</code> priority.
*/
public boolean isWarnEnabled() {
return getLogger().isEnabledFor(Priority.WARN);
}
}

View File

@@ -1,294 +0,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.
*/
package org.apache.commons.logging.impl;
import java.io.Serializable;
import org.apache.log.Logger;
import org.apache.log.Hierarchy;
import org.apache.commons.logging.Log;
/**
* <p>Implementation of <code>org.apache.commons.logging.Log</code>
* that wraps the <a href="http://avalon.apache.org/logkit/">avalon-logkit</a>
* logging system. Configuration of <code>LogKit</code> is left to the user.
* </p>
*
* <p><code>LogKit</code> accepts only <code>String</code> messages.
* Therefore, this implementation converts object messages into strings
* by called their <code>toString()</code> method before logging them.</p>
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Robert Burrell Donkin
* @version $Id: LogKitLogger.java 424107 2006-07-20 23:15:42Z skitching $
*/
public class LogKitLogger implements Log, Serializable {
// ------------------------------------------------------------- Attributes
/** Logging goes to this <code>LogKit</code> logger */
protected transient Logger logger = null;
/** Name of this logger */
protected String name = null;
// ------------------------------------------------------------ Constructor
/**
* Construct <code>LogKitLogger</code> which wraps the <code>LogKit</code>
* logger with given name.
*
* @param name log name
*/
public LogKitLogger(String name) {
this.name = name;
this.logger = getLogger();
}
// --------------------------------------------------------- Public Methods
/**
* <p>Return the underlying Logger we are using.</p>
*/
public Logger getLogger() {
if (logger == null) {
logger = Hierarchy.getDefaultHierarchy().getLoggerFor(name);
}
return (logger);
}
// ----------------------------------------------------- Log Implementation
/**
* Logs a message with <code>org.apache.log.Priority.DEBUG</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#trace(Object)
*/
public void trace(Object message) {
debug(message);
}
/**
* Logs a message with <code>org.apache.log.Priority.DEBUG</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#trace(Object, Throwable)
*/
public void trace(Object message, Throwable t) {
debug(message, t);
}
/**
* Logs a message with <code>org.apache.log.Priority.DEBUG</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#debug(Object)
*/
public void debug(Object message) {
if (message != null) {
getLogger().debug(String.valueOf(message));
}
}
/**
* Logs a message with <code>org.apache.log.Priority.DEBUG</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#debug(Object, Throwable)
*/
public void debug(Object message, Throwable t) {
if (message != null) {
getLogger().debug(String.valueOf(message), t);
}
}
/**
* Logs a message with <code>org.apache.log.Priority.INFO</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#info(Object)
*/
public void info(Object message) {
if (message != null) {
getLogger().info(String.valueOf(message));
}
}
/**
* Logs a message with <code>org.apache.log.Priority.INFO</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#info(Object, Throwable)
*/
public void info(Object message, Throwable t) {
if (message != null) {
getLogger().info(String.valueOf(message), t);
}
}
/**
* Logs a message with <code>org.apache.log.Priority.WARN</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#warn(Object)
*/
public void warn(Object message) {
if (message != null) {
getLogger().warn(String.valueOf(message));
}
}
/**
* Logs a message with <code>org.apache.log.Priority.WARN</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#warn(Object, Throwable)
*/
public void warn(Object message, Throwable t) {
if (message != null) {
getLogger().warn(String.valueOf(message), t);
}
}
/**
* Logs a message with <code>org.apache.log.Priority.ERROR</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#error(Object)
*/
public void error(Object message) {
if (message != null) {
getLogger().error(String.valueOf(message));
}
}
/**
* Logs a message with <code>org.apache.log.Priority.ERROR</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#error(Object, Throwable)
*/
public void error(Object message, Throwable t) {
if (message != null) {
getLogger().error(String.valueOf(message), t);
}
}
/**
* Logs a message with <code>org.apache.log.Priority.FATAL_ERROR</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#fatal(Object)
*/
public void fatal(Object message) {
if (message != null) {
getLogger().fatalError(String.valueOf(message));
}
}
/**
* Logs a message with <code>org.apache.log.Priority.FATAL_ERROR</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#fatal(Object, Throwable)
*/
public void fatal(Object message, Throwable t) {
if (message != null) {
getLogger().fatalError(String.valueOf(message), t);
}
}
/**
* Checks whether the <code>LogKit</code> logger will log messages of priority <code>DEBUG</code>.
*/
public boolean isDebugEnabled() {
return getLogger().isDebugEnabled();
}
/**
* Checks whether the <code>LogKit</code> logger will log messages of priority <code>ERROR</code>.
*/
public boolean isErrorEnabled() {
return getLogger().isErrorEnabled();
}
/**
* Checks whether the <code>LogKit</code> logger will log messages of priority <code>FATAL_ERROR</code>.
*/
public boolean isFatalEnabled() {
return getLogger().isFatalErrorEnabled();
}
/**
* Checks whether the <code>LogKit</code> logger will log messages of priority <code>INFO</code>.
*/
public boolean isInfoEnabled() {
return getLogger().isInfoEnabled();
}
/**
* Checks whether the <code>LogKit</code> logger will log messages of priority <code>DEBUG</code>.
*/
public boolean isTraceEnabled() {
return getLogger().isDebugEnabled();
}
/**
* Checks whether the <code>LogKit</code> logger will log messages of priority <code>WARN</code>.
*/
public boolean isWarnEnabled() {
return getLogger().isWarnEnabled();
}
}

View File

@@ -1,107 +0,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.
*/
package org.apache.commons.logging.impl;
import java.io.Serializable;
import org.apache.commons.logging.Log;
/**
* <p>Trivial implementation of Log that throws away all messages. No
* configurable system properties are supported.</p>
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
* @version $Id: NoOpLog.java 424107 2006-07-20 23:15:42Z skitching $
*/
public class NoOpLog implements Log, Serializable {
/** Convenience constructor */
public NoOpLog() { }
/** Base constructor */
public NoOpLog(String name) { }
/** Do nothing */
public void trace(Object message) { }
/** Do nothing */
public void trace(Object message, Throwable t) { }
/** Do nothing */
public void debug(Object message) { }
/** Do nothing */
public void debug(Object message, Throwable t) { }
/** Do nothing */
public void info(Object message) { }
/** Do nothing */
public void info(Object message, Throwable t) { }
/** Do nothing */
public void warn(Object message) { }
/** Do nothing */
public void warn(Object message, Throwable t) { }
/** Do nothing */
public void error(Object message) { }
/** Do nothing */
public void error(Object message, Throwable t) { }
/** Do nothing */
public void fatal(Object message) { }
/** Do nothing */
public void fatal(Object message, Throwable t) { }
/**
* Debug is never enabled.
*
* @return false
*/
public final boolean isDebugEnabled() { return false; }
/**
* Error is never enabled.
*
* @return false
*/
public final boolean isErrorEnabled() { return false; }
/**
* Fatal is never enabled.
*
* @return false
*/
public final boolean isFatalEnabled() { return false; }
/**
* Info is never enabled.
*
* @return false
*/
public final boolean isInfoEnabled() { return false; }
/**
* Trace is never enabled.
*
* @return false
*/
public final boolean isTraceEnabled() { return false; }
/**
* Warn is never enabled.
*
* @return false
*/
public final boolean isWarnEnabled() { return false; }
}

View File

@@ -1,138 +0,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.
*/
package org.apache.commons.logging.impl;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import org.apache.commons.logging.LogFactory;
/**
* This class is capable of receiving notifications about the undeployment of
* a webapp, and responds by ensuring that commons-logging releases all
* memory associated with the undeployed webapp.
* <p>
* In general, the WeakHashtable support added in commons-logging release 1.1
* ensures that logging classes do not hold references that prevent an
* undeployed webapp's memory from being garbage-collected even when multiple
* copies of commons-logging are deployed via multiple classloaders (a
* situation that earlier versions had problems with). However there are
* some rare cases where the WeakHashtable approach does not work; in these
* situations specifying this class as a listener for the web application will
* ensure that all references held by commons-logging are fully released.
* <p>
* To use this class, configure the webapp deployment descriptor to call
* this class on webapp undeploy; the contextDestroyed method will tell
* every accessable LogFactory class that the entry in its map for the
* current webapp's context classloader should be cleared.
*
* @since 1.1
*/
public class ServletContextCleaner implements ServletContextListener {
private Class[] RELEASE_SIGNATURE = {ClassLoader.class};
/**
* Invoked when a webapp is undeployed, this tells the LogFactory
* class to release any logging information related to the current
* contextClassloader.
*/
public void contextDestroyed(ServletContextEvent sce) {
ClassLoader tccl = Thread.currentThread().getContextClassLoader();
Object[] params = new Object[1];
params[0] = tccl;
// Walk up the tree of classloaders, finding all the available
// LogFactory classes and releasing any objects associated with
// the tccl (ie the webapp).
//
// When there is only one LogFactory in the classpath, and it
// is within the webapp being undeployed then there is no problem;
// garbage collection works fine.
//
// When there are multiple LogFactory classes in the classpath but
// parent-first classloading is used everywhere, this loop is really
// short. The first instance of LogFactory found will
// be the highest in the classpath, and then no more will be found.
// This is ok, as with this setup this will be the only LogFactory
// holding any data associated with the tccl being released.
//
// When there are multiple LogFactory classes in the classpath and
// child-first classloading is used in any classloader, then multiple
// LogFactory instances may hold info about this TCCL; whenever the
// webapp makes a call into a class loaded via an ancestor classloader
// and that class calls LogFactory the tccl gets registered in
// the LogFactory instance that is visible from the ancestor
// classloader. However the concrete logging library it points
// to is expected to have been loaded via the TCCL, so the
// underlying logging lib is only initialised/configured once.
// These references from ancestor LogFactory classes down to
// TCCL classloaders are held via weak references and so should
// be released but there are circumstances where they may not.
// Walking up the classloader ancestry ladder releasing
// the current tccl at each level tree, though, will definitely
// clear any problem references.
ClassLoader loader = tccl;
while (loader != null) {
// Load via the current loader. Note that if the class is not accessable
// via this loader, but is accessable via some ancestor then that class
// will be returned.
try {
Class logFactoryClass = loader.loadClass("org.apache.commons.logging.LogFactory");
Method releaseMethod = logFactoryClass.getMethod("release", RELEASE_SIGNATURE);
releaseMethod.invoke(null, params);
loader = logFactoryClass.getClassLoader().getParent();
} catch(ClassNotFoundException ex) {
// Neither the current classloader nor any of its ancestors could find
// the LogFactory class, so we can stop now.
loader = null;
} catch(NoSuchMethodException ex) {
// This is not expected; every version of JCL has this method
System.err.println("LogFactory instance found which does not support release method!");
loader = null;
} catch(IllegalAccessException ex) {
// This is not expected; every ancestor class should be accessable
System.err.println("LogFactory instance found which is not accessable!");
loader = null;
} catch(InvocationTargetException ex) {
// This is not expected
System.err.println("LogFactory instance release method failed!");
loader = null;
}
}
// Just to be sure, invoke release on the LogFactory that is visible from
// this ServletContextCleaner class too. This should already have been caught
// by the above loop but just in case...
LogFactory.release(tccl);
}
/**
* Invoked when a webapp is deployed. Nothing needs to be done here.
*/
public void contextInitialized(ServletContextEvent sce) {
// do nothing
}
}

View File

@@ -1,721 +0,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.
*/
package org.apache.commons.logging.impl;
import java.io.InputStream;
import java.io.Serializable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Properties;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogConfigurationException;
/**
* <p>Simple implementation of Log that sends all enabled log messages,
* for all defined loggers, to System.err. The following system properties
* are supported to configure the behavior of this logger:</p>
* <ul>
* <li><code>org.apache.commons.logging.simplelog.defaultlog</code> -
* Default logging detail level for all instances of SimpleLog.
* Must be one of ("trace", "debug", "info", "warn", "error", or "fatal").
* If not specified, defaults to "info". </li>
* <li><code>org.apache.commons.logging.simplelog.log.xxxxx</code> -
* Logging detail level for a SimpleLog instance named "xxxxx".
* Must be one of ("trace", "debug", "info", "warn", "error", or "fatal").
* If not specified, the default logging detail level is used.</li>
* <li><code>org.apache.commons.logging.simplelog.showlogname</code> -
* Set to <code>true</code> if you want the Log instance name to be
* included in output messages. Defaults to <code>false</code>.</li>
* <li><code>org.apache.commons.logging.simplelog.showShortLogname</code> -
* Set to <code>true</code> if you want the last component of the name to be
* included in output messages. Defaults to <code>true</code>.</li>
* <li><code>org.apache.commons.logging.simplelog.showdatetime</code> -
* Set to <code>true</code> if you want the current date and time
* to be included in output messages. Default is <code>false</code>.</li>
* <li><code>org.apache.commons.logging.simplelog.dateTimeFormat</code> -
* The date and time format to be used in the output messages.
* The pattern describing the date and time format is the same that is
* used in <code>java.text.SimpleDateFormat</code>. If the format is not
* specified or is invalid, the default format is used.
* The default format is <code>yyyy/MM/dd HH:mm:ss:SSS zzz</code>.</li>
* </ul>
*
* <p>In addition to looking for system properties with the names specified
* above, this implementation also checks for a class loader resource named
* <code>"simplelog.properties"</code>, and includes any matching definitions
* from this resource (if it exists).</p>
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
* @author Robert Burrell Donkin
*
* @version $Id: SimpleLog.java 581090 2007-10-01 22:01:06Z dennisl $
*/
public class SimpleLog implements Log, Serializable {
// ------------------------------------------------------- Class Attributes
/** All system properties used by <code>SimpleLog</code> start with this */
static protected final String systemPrefix =
"org.apache.commons.logging.simplelog.";
/** Properties loaded from simplelog.properties */
static protected final Properties simpleLogProps = new Properties();
/** The default format to use when formating dates */
static protected final String DEFAULT_DATE_TIME_FORMAT =
"yyyy/MM/dd HH:mm:ss:SSS zzz";
/** Include the instance name in the log message? */
static protected boolean showLogName = false;
/** Include the short name ( last component ) of the logger in the log
* message. Defaults to true - otherwise we'll be lost in a flood of
* messages without knowing who sends them.
*/
static protected boolean showShortName = true;
/** Include the current time in the log message */
static protected boolean showDateTime = false;
/** The date and time format to use in the log message */
static protected String dateTimeFormat = DEFAULT_DATE_TIME_FORMAT;
/**
* Used to format times.
* <p>
* Any code that accesses this object should first obtain a lock on it,
* ie use synchronized(dateFormatter); this requirement was introduced
* in 1.1.1 to fix an existing thread safety bug (SimpleDateFormat.format
* is not thread-safe).
*/
static protected DateFormat dateFormatter = null;
// ---------------------------------------------------- Log Level Constants
/** "Trace" level logging. */
public static final int LOG_LEVEL_TRACE = 1;
/** "Debug" level logging. */
public static final int LOG_LEVEL_DEBUG = 2;
/** "Info" level logging. */
public static final int LOG_LEVEL_INFO = 3;
/** "Warn" level logging. */
public static final int LOG_LEVEL_WARN = 4;
/** "Error" level logging. */
public static final int LOG_LEVEL_ERROR = 5;
/** "Fatal" level logging. */
public static final int LOG_LEVEL_FATAL = 6;
/** Enable all logging levels */
public static final int LOG_LEVEL_ALL = (LOG_LEVEL_TRACE - 1);
/** Enable no logging levels */
public static final int LOG_LEVEL_OFF = (LOG_LEVEL_FATAL + 1);
// ------------------------------------------------------------ Initializer
private static String getStringProperty(String name) {
String prop = null;
try {
prop = System.getProperty(name);
} catch (SecurityException e) {
; // Ignore
}
return (prop == null) ? simpleLogProps.getProperty(name) : prop;
}
private static String getStringProperty(String name, String dephault) {
String prop = getStringProperty(name);
return (prop == null) ? dephault : prop;
}
private static boolean getBooleanProperty(String name, boolean dephault) {
String prop = getStringProperty(name);
return (prop == null) ? dephault : "true".equalsIgnoreCase(prop);
}
// Initialize class attributes.
// Load properties file, if found.
// Override with system properties.
static {
// Add props from the resource simplelog.properties
InputStream in = getResourceAsStream("simplelog.properties");
if(null != in) {
try {
simpleLogProps.load(in);
in.close();
} catch(java.io.IOException e) {
// ignored
}
}
showLogName = getBooleanProperty( systemPrefix + "showlogname", showLogName);
showShortName = getBooleanProperty( systemPrefix + "showShortLogname", showShortName);
showDateTime = getBooleanProperty( systemPrefix + "showdatetime", showDateTime);
if(showDateTime) {
dateTimeFormat = getStringProperty(systemPrefix + "dateTimeFormat",
dateTimeFormat);
try {
dateFormatter = new SimpleDateFormat(dateTimeFormat);
} catch(IllegalArgumentException e) {
// If the format pattern is invalid - use the default format
dateTimeFormat = DEFAULT_DATE_TIME_FORMAT;
dateFormatter = new SimpleDateFormat(dateTimeFormat);
}
}
}
// ------------------------------------------------------------- Attributes
/** The name of this simple log instance */
protected String logName = null;
/** The current log level */
protected int currentLogLevel;
/** The short name of this simple log instance */
private String shortLogName = null;
// ------------------------------------------------------------ Constructor
/**
* Construct a simple log with given name.
*
* @param name log name
*/
public SimpleLog(String name) {
logName = name;
// Set initial log level
// Used to be: set default log level to ERROR
// IMHO it should be lower, but at least info ( costin ).
setLevel(SimpleLog.LOG_LEVEL_INFO);
// Set log level from properties
String lvl = getStringProperty(systemPrefix + "log." + logName);
int i = String.valueOf(name).lastIndexOf(".");
while(null == lvl && i > -1) {
name = name.substring(0,i);
lvl = getStringProperty(systemPrefix + "log." + name);
i = String.valueOf(name).lastIndexOf(".");
}
if(null == lvl) {
lvl = getStringProperty(systemPrefix + "defaultlog");
}
if("all".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_ALL);
} else if("trace".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_TRACE);
} else if("debug".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_DEBUG);
} else if("info".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_INFO);
} else if("warn".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_WARN);
} else if("error".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_ERROR);
} else if("fatal".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_FATAL);
} else if("off".equalsIgnoreCase(lvl)) {
setLevel(SimpleLog.LOG_LEVEL_OFF);
}
}
// -------------------------------------------------------- Properties
/**
* <p> Set logging level. </p>
*
* @param currentLogLevel new logging level
*/
public void setLevel(int currentLogLevel) {
this.currentLogLevel = currentLogLevel;
}
/**
* <p> Get logging level. </p>
*/
public int getLevel() {
return currentLogLevel;
}
// -------------------------------------------------------- Logging Methods
/**
* <p> Do the actual logging.
* This method assembles the message
* and then calls <code>write()</code> to cause it to be written.</p>
*
* @param type One of the LOG_LEVEL_XXX constants defining the log level
* @param message The message itself (typically a String)
* @param t The exception whose stack trace should be logged
*/
protected void log(int type, Object message, Throwable t) {
// Use a string buffer for better performance
StringBuffer buf = new StringBuffer();
// Append date-time if so configured
if(showDateTime) {
Date now = new Date();
String dateText;
synchronized(dateFormatter) {
dateText = dateFormatter.format(now);
}
buf.append(dateText);
buf.append(" ");
}
// Append a readable representation of the log level
switch(type) {
case SimpleLog.LOG_LEVEL_TRACE: buf.append("[TRACE] "); break;
case SimpleLog.LOG_LEVEL_DEBUG: buf.append("[DEBUG] "); break;
case SimpleLog.LOG_LEVEL_INFO: buf.append("[INFO] "); break;
case SimpleLog.LOG_LEVEL_WARN: buf.append("[WARN] "); break;
case SimpleLog.LOG_LEVEL_ERROR: buf.append("[ERROR] "); break;
case SimpleLog.LOG_LEVEL_FATAL: buf.append("[FATAL] "); break;
}
// Append the name of the log instance if so configured
if( showShortName) {
if( shortLogName==null ) {
// Cut all but the last component of the name for both styles
shortLogName = logName.substring(logName.lastIndexOf(".") + 1);
shortLogName =
shortLogName.substring(shortLogName.lastIndexOf("/") + 1);
}
buf.append(String.valueOf(shortLogName)).append(" - ");
} else if(showLogName) {
buf.append(String.valueOf(logName)).append(" - ");
}
// Append the message
buf.append(String.valueOf(message));
// Append stack trace if not null
if(t != null) {
buf.append(" <");
buf.append(t.toString());
buf.append(">");
java.io.StringWriter sw= new java.io.StringWriter(1024);
java.io.PrintWriter pw= new java.io.PrintWriter(sw);
t.printStackTrace(pw);
pw.close();
buf.append(sw.toString());
}
// Print to the appropriate destination
write(buf);
}
/**
* <p>Write the content of the message accumulated in the specified
* <code>StringBuffer</code> to the appropriate output destination. The
* default implementation writes to <code>System.err</code>.</p>
*
* @param buffer A <code>StringBuffer</code> containing the accumulated
* text to be logged
*/
protected void write(StringBuffer buffer) {
System.err.println(buffer.toString());
}
/**
* Is the given log level currently enabled?
*
* @param logLevel is this level enabled?
*/
protected boolean isLevelEnabled(int logLevel) {
// log level are numerically ordered so can use simple numeric
// comparison
return (logLevel >= currentLogLevel);
}
// -------------------------------------------------------- Log Implementation
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_DEBUG</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#debug(Object)
*/
public final void debug(Object message) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_DEBUG)) {
log(SimpleLog.LOG_LEVEL_DEBUG, message, null);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_DEBUG</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#debug(Object, Throwable)
*/
public final void debug(Object message, Throwable t) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_DEBUG)) {
log(SimpleLog.LOG_LEVEL_DEBUG, message, t);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_TRACE</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#trace(Object)
*/
public final void trace(Object message) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_TRACE)) {
log(SimpleLog.LOG_LEVEL_TRACE, message, null);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_TRACE</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#trace(Object, Throwable)
*/
public final void trace(Object message, Throwable t) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_TRACE)) {
log(SimpleLog.LOG_LEVEL_TRACE, message, t);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_INFO</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#info(Object)
*/
public final void info(Object message) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_INFO)) {
log(SimpleLog.LOG_LEVEL_INFO,message,null);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_INFO</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#info(Object, Throwable)
*/
public final void info(Object message, Throwable t) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_INFO)) {
log(SimpleLog.LOG_LEVEL_INFO, message, t);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_WARN</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#warn(Object)
*/
public final void warn(Object message) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_WARN)) {
log(SimpleLog.LOG_LEVEL_WARN, message, null);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_WARN</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#warn(Object, Throwable)
*/
public final void warn(Object message, Throwable t) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_WARN)) {
log(SimpleLog.LOG_LEVEL_WARN, message, t);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_ERROR</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#error(Object)
*/
public final void error(Object message) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_ERROR)) {
log(SimpleLog.LOG_LEVEL_ERROR, message, null);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_ERROR</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#error(Object, Throwable)
*/
public final void error(Object message, Throwable t) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_ERROR)) {
log(SimpleLog.LOG_LEVEL_ERROR, message, t);
}
}
/**
* Log a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_FATAL</code>.
*
* @param message to log
* @see org.apache.commons.logging.Log#fatal(Object)
*/
public final void fatal(Object message) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_FATAL)) {
log(SimpleLog.LOG_LEVEL_FATAL, message, null);
}
}
/**
* Logs a message with
* <code>org.apache.commons.logging.impl.SimpleLog.LOG_LEVEL_FATAL</code>.
*
* @param message to log
* @param t log this cause
* @see org.apache.commons.logging.Log#fatal(Object, Throwable)
*/
public final void fatal(Object message, Throwable t) {
if (isLevelEnabled(SimpleLog.LOG_LEVEL_FATAL)) {
log(SimpleLog.LOG_LEVEL_FATAL, message, t);
}
}
/**
* <p> Are debug messages currently enabled? </p>
*
* <p> This allows expensive operations such as <code>String</code>
* concatenation to be avoided when the message will be ignored by the
* logger. </p>
*/
public final boolean isDebugEnabled() {
return isLevelEnabled(SimpleLog.LOG_LEVEL_DEBUG);
}
/**
* <p> Are error messages currently enabled? </p>
*
* <p> This allows expensive operations such as <code>String</code>
* concatenation to be avoided when the message will be ignored by the
* logger. </p>
*/
public final boolean isErrorEnabled() {
return isLevelEnabled(SimpleLog.LOG_LEVEL_ERROR);
}
/**
* <p> Are fatal messages currently enabled? </p>
*
* <p> This allows expensive operations such as <code>String</code>
* concatenation to be avoided when the message will be ignored by the
* logger. </p>
*/
public final boolean isFatalEnabled() {
return isLevelEnabled(SimpleLog.LOG_LEVEL_FATAL);
}
/**
* <p> Are info messages currently enabled? </p>
*
* <p> This allows expensive operations such as <code>String</code>
* concatenation to be avoided when the message will be ignored by the
* logger. </p>
*/
public final boolean isInfoEnabled() {
return isLevelEnabled(SimpleLog.LOG_LEVEL_INFO);
}
/**
* <p> Are trace messages currently enabled? </p>
*
* <p> This allows expensive operations such as <code>String</code>
* concatenation to be avoided when the message will be ignored by the
* logger. </p>
*/
public final boolean isTraceEnabled() {
return isLevelEnabled(SimpleLog.LOG_LEVEL_TRACE);
}
/**
* <p> Are warn messages currently enabled? </p>
*
* <p> This allows expensive operations such as <code>String</code>
* concatenation to be avoided when the message will be ignored by the
* logger. </p>
*/
public final boolean isWarnEnabled() {
return isLevelEnabled(SimpleLog.LOG_LEVEL_WARN);
}
/**
* Return the thread context class loader if available.
* Otherwise return null.
*
* The thread context class loader is available for JDK 1.2
* or later, if certain security conditions are met.
*
* @exception LogConfigurationException if a suitable class loader
* cannot be identified.
*/
private static ClassLoader getContextClassLoader()
{
ClassLoader classLoader = null;
if (classLoader == null) {
try {
// Are we running on a JDK 1.2 or later system?
Method method = Thread.class.getMethod("getContextClassLoader",
(Class[]) null);
// Get the thread context class loader (if there is one)
try {
classLoader = (ClassLoader)method.invoke(Thread.currentThread(),
(Class[]) null);
} catch (IllegalAccessException e) {
; // ignore
} catch (InvocationTargetException e) {
/**
* InvocationTargetException is thrown by 'invoke' when
* the method being invoked (getContextClassLoader) throws
* an exception.
*
* getContextClassLoader() throws SecurityException when
* the context class loader isn't an ancestor of the
* calling class's class loader, or if security
* permissions are restricted.
*
* In the first case (not related), we want to ignore and
* keep going. We cannot help but also ignore the second
* with the logic below, but other calls elsewhere (to
* obtain a class loader) will trigger this exception where
* we can make a distinction.
*/
if (e.getTargetException() instanceof SecurityException) {
; // ignore
} else {
// Capture 'e.getTargetException()' exception for details
// alternate: log 'e.getTargetException()', and pass back 'e'.
throw new LogConfigurationException
("Unexpected InvocationTargetException", e.getTargetException());
}
}
} catch (NoSuchMethodException e) {
// Assume we are running on JDK 1.1
; // ignore
}
}
if (classLoader == null) {
classLoader = SimpleLog.class.getClassLoader();
}
// Return the selected class loader
return classLoader;
}
private static InputStream getResourceAsStream(final String name)
{
return (InputStream)AccessController.doPrivileged(
new PrivilegedAction() {
public Object run() {
ClassLoader threadCL = getContextClassLoader();
if (threadCL != null) {
return threadCL.getResourceAsStream(name);
} else {
return ClassLoader.getSystemResourceAsStream(name);
}
}
});
}
}

View File

@@ -1,478 +0,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.
*/
package org.apache.commons.logging.impl;
import java.lang.ref.ReferenceQueue;
import java.lang.ref.WeakReference;
import java.util.*;
/**
* <p>Implementation of <code>Hashtable</code> that uses <code>WeakReference</code>'s
* to hold its keys thus allowing them to be reclaimed by the garbage collector.
* The associated values are retained using strong references.</p>
*
* <p>This class follows the symantics of <code>Hashtable</code> as closely as
* possible. It therefore does not accept null values or keys.</p>
*
* <p><strong>Note:</strong>
* This is <em>not</em> intended to be a general purpose hash table replacement.
* This implementation is also tuned towards a particular purpose: for use as a replacement
* for <code>Hashtable</code> in <code>LogFactory</code>. This application requires
* good liveliness for <code>get</code> and <code>put</code>. Various tradeoffs
* have been made with this in mind.
* </p>
* <p>
* <strong>Usage:</strong> typical use case is as a drop-in replacement
* for the <code>Hashtable</code> used in <code>LogFactory</code> for J2EE enviroments
* running 1.3+ JVMs. Use of this class <i>in most cases</i> (see below) will
* allow classloaders to be collected by the garbage collector without the need
* to call {@link org.apache.commons.logging.LogFactory#release(ClassLoader) LogFactory.release(ClassLoader)}.
* </p>
*
* <p><code>org.apache.commons.logging.LogFactory</code> checks whether this class
* can be supported by the current JVM, and if so then uses it to store
* references to the <code>LogFactory</code> implementationd it loads
* (rather than using a standard Hashtable instance).
* Having this class used instead of <code>Hashtable</code> solves
* certain issues related to dynamic reloading of applications in J2EE-style
* environments. However this class requires java 1.3 or later (due to its use
* of <code>java.lang.ref.WeakReference</code> and associates).
* And by the way, this extends <code>Hashtable</code> rather than <code>HashMap</code>
* for backwards compatibility reasons. See the documentation
* for method <code>LogFactory.createFactoryStore</code> for more details.</p>
*
* <p>The reason all this is necessary is due to a issue which
* arises during hot deploy in a J2EE-like containers.
* Each component running in the container owns one or more classloaders; when
* the component loads a LogFactory instance via the component classloader
* a reference to it gets stored in the static LogFactory.factories member,
* keyed by the component's classloader so different components don't
* stomp on each other. When the component is later unloaded, the container
* sets the component's classloader to null with the intent that all the
* component's classes get garbage-collected. However there's still a
* reference to the component's classloader from a key in the "global"
* <code>LogFactory</code>'s factories member! If <code>LogFactory.release()</code>
* is called whenever component is unloaded, the classloaders will be correctly
* garbage collected; this <i>should</i> be done by any container that
* bundles commons-logging by default. However, holding the classloader
* references weakly ensures that the classloader will be garbage collected
* without the container performing this step. </p>
*
* <p>
* <strong>Limitations:</strong>
* There is still one (unusual) scenario in which a component will not
* be correctly unloaded without an explicit release. Though weak references
* are used for its keys, it is necessary to use strong references for its values.
* </p>
*
* <p> If the abstract class <code>LogFactory</code> is
* loaded by the container classloader but a subclass of
* <code>LogFactory</code> [LogFactory1] is loaded by the component's
* classloader and an instance stored in the static map associated with the
* base LogFactory class, then there is a strong reference from the LogFactory
* class to the LogFactory1 instance (as normal) and a strong reference from
* the LogFactory1 instance to the component classloader via
* <code>getClass().getClassLoader()</code>. This chain of references will prevent
* collection of the child classloader.</p>
*
* <p>
* Such a situation occurs when the commons-logging.jar is
* loaded by a parent classloader (e.g. a server level classloader in a
* servlet container) and a custom <code>LogFactory</code> implementation is
* loaded by a child classloader (e.g. a web app classloader).</p>
*
* <p>To avoid this scenario, ensure
* that any custom LogFactory subclass is loaded by the same classloader as
* the base <code>LogFactory</code>. Creating custom LogFactory subclasses is,
* however, rare. The standard LogFactoryImpl class should be sufficient
* for most or all users.</p>
*
*
* @author Brian Stansberry
*
* @since 1.1
*/
public final class WeakHashtable extends Hashtable {
/**
* The maximum number of times put() or remove() can be called before
* the map will be purged of all cleared entries.
*/
private static final int MAX_CHANGES_BEFORE_PURGE = 100;
/**
* The maximum number of times put() or remove() can be called before
* the map will be purged of one cleared entry.
*/
private static final int PARTIAL_PURGE_COUNT = 10;
/* ReferenceQueue we check for gc'd keys */
private ReferenceQueue queue = new ReferenceQueue();
/* Counter used to control how often we purge gc'd entries */
private int changeCount = 0;
/**
* Constructs a WeakHashtable with the Hashtable default
* capacity and load factor.
*/
public WeakHashtable() {}
/**
*@see Hashtable
*/
public boolean containsKey(Object key) {
// purge should not be required
Referenced referenced = new Referenced(key);
return super.containsKey(referenced);
}
/**
*@see Hashtable
*/
public Enumeration elements() {
purge();
return super.elements();
}
/**
*@see Hashtable
*/
public Set entrySet() {
purge();
Set referencedEntries = super.entrySet();
Set unreferencedEntries = new HashSet();
for (Iterator it=referencedEntries.iterator(); it.hasNext();) {
Map.Entry entry = (Map.Entry) it.next();
Referenced referencedKey = (Referenced) entry.getKey();
Object key = referencedKey.getValue();
Object value = entry.getValue();
if (key != null) {
Entry dereferencedEntry = new Entry(key, value);
unreferencedEntries.add(dereferencedEntry);
}
}
return unreferencedEntries;
}
/**
*@see Hashtable
*/
public Object get(Object key) {
// for performance reasons, no purge
Referenced referenceKey = new Referenced(key);
return super.get(referenceKey);
}
/**
*@see Hashtable
*/
public Enumeration keys() {
purge();
final Enumeration enumer = super.keys();
return new Enumeration() {
public boolean hasMoreElements() {
return enumer.hasMoreElements();
}
public Object nextElement() {
Referenced nextReference = (Referenced) enumer.nextElement();
return nextReference.getValue();
}
};
}
/**
*@see Hashtable
*/
public Set keySet() {
purge();
Set referencedKeys = super.keySet();
Set unreferencedKeys = new HashSet();
for (Iterator it=referencedKeys.iterator(); it.hasNext();) {
Referenced referenceKey = (Referenced) it.next();
Object keyValue = referenceKey.getValue();
if (keyValue != null) {
unreferencedKeys.add(keyValue);
}
}
return unreferencedKeys;
}
/**
*@see Hashtable
*/
public Object put(Object key, Object value) {
// check for nulls, ensuring symantics match superclass
if (key == null) {
throw new NullPointerException("Null keys are not allowed");
}
if (value == null) {
throw new NullPointerException("Null values are not allowed");
}
// for performance reasons, only purge every
// MAX_CHANGES_BEFORE_PURGE times
if (changeCount++ > MAX_CHANGES_BEFORE_PURGE) {
purge();
changeCount = 0;
}
// do a partial purge more often
else if ((changeCount % PARTIAL_PURGE_COUNT) == 0) {
purgeOne();
}
Referenced keyRef = new Referenced(key, queue);
return super.put(keyRef, value);
}
/**
*@see Hashtable
*/
public void putAll(Map t) {
if (t != null) {
Set entrySet = t.entrySet();
for (Iterator it=entrySet.iterator(); it.hasNext();) {
Map.Entry entry = (Map.Entry) it.next();
put(entry.getKey(), entry.getValue());
}
}
}
/**
*@see Hashtable
*/
public Collection values() {
purge();
return super.values();
}
/**
*@see Hashtable
*/
public Object remove(Object key) {
// for performance reasons, only purge every
// MAX_CHANGES_BEFORE_PURGE times
if (changeCount++ > MAX_CHANGES_BEFORE_PURGE) {
purge();
changeCount = 0;
}
// do a partial purge more often
else if ((changeCount % PARTIAL_PURGE_COUNT) == 0) {
purgeOne();
}
return super.remove(new Referenced(key));
}
/**
*@see Hashtable
*/
public boolean isEmpty() {
purge();
return super.isEmpty();
}
/**
*@see Hashtable
*/
public int size() {
purge();
return super.size();
}
/**
*@see Hashtable
*/
public String toString() {
purge();
return super.toString();
}
/**
* @see Hashtable
*/
protected void rehash() {
// purge here to save the effort of rehashing dead entries
purge();
super.rehash();
}
/**
* Purges all entries whose wrapped keys
* have been garbage collected.
*/
private void purge() {
synchronized (queue) {
WeakKey key;
while ((key = (WeakKey) queue.poll()) != null) {
super.remove(key.getReferenced());
}
}
}
/**
* Purges one entry whose wrapped key
* has been garbage collected.
*/
private void purgeOne() {
synchronized (queue) {
WeakKey key = (WeakKey) queue.poll();
if (key != null) {
super.remove(key.getReferenced());
}
}
}
/** Entry implementation */
private final static class Entry implements Map.Entry {
private final Object key;
private final Object value;
private Entry(Object key, Object value) {
this.key = key;
this.value = value;
}
public boolean equals(Object o) {
boolean result = false;
if (o != null && o instanceof Map.Entry) {
Map.Entry entry = (Map.Entry) o;
result = (getKey()==null ?
entry.getKey() == null :
getKey().equals(entry.getKey()))
&&
(getValue()==null ?
entry.getValue() == null :
getValue().equals(entry.getValue()));
}
return result;
}
public int hashCode() {
return (getKey()==null ? 0 : getKey().hashCode()) ^
(getValue()==null ? 0 : getValue().hashCode());
}
public Object setValue(Object value) {
throw new UnsupportedOperationException("Entry.setValue is not supported.");
}
public Object getValue() {
return value;
}
public Object getKey() {
return key;
}
}
/** Wrapper giving correct symantics for equals and hashcode */
private final static class Referenced {
private final WeakReference reference;
private final int hashCode;
/**
*
* @throws NullPointerException if referant is <code>null</code>
*/
private Referenced(Object referant) {
reference = new WeakReference(referant);
// Calc a permanent hashCode so calls to Hashtable.remove()
// work if the WeakReference has been cleared
hashCode = referant.hashCode();
}
/**
*
* @throws NullPointerException if key is <code>null</code>
*/
private Referenced(Object key, ReferenceQueue queue) {
reference = new WeakKey(key, queue, this);
// Calc a permanent hashCode so calls to Hashtable.remove()
// work if the WeakReference has been cleared
hashCode = key.hashCode();
}
public int hashCode() {
return hashCode;
}
private Object getValue() {
return reference.get();
}
public boolean equals(Object o) {
boolean result = false;
if (o instanceof Referenced) {
Referenced otherKey = (Referenced) o;
Object thisKeyValue = getValue();
Object otherKeyValue = otherKey.getValue();
if (thisKeyValue == null) {
result = (otherKeyValue == null);
// Since our hashcode was calculated from the original
// non-null referant, the above check breaks the
// hashcode/equals contract, as two cleared Referenced
// objects could test equal but have different hashcodes.
// We can reduce (not eliminate) the chance of this
// happening by comparing hashcodes.
if (result == true) {
result = (this.hashCode() == otherKey.hashCode());
}
// In any case, as our c'tor does not allow null referants
// and Hashtable does not do equality checks between
// existing keys, normal hashtable operations should never
// result in an equals comparison between null referants
}
else
{
result = thisKeyValue.equals(otherKeyValue);
}
}
return result;
}
}
/**
* WeakReference subclass that holds a hard reference to an
* associated <code>value</code> and also makes accessible
* the Referenced object holding it.
*/
private final static class WeakKey extends WeakReference {
private final Referenced referenced;
private WeakKey(Object key,
ReferenceQueue queue,
Referenced referenced) {
super(key, queue);
this.referenced = referenced;
}
private Referenced getReferenced() {
return referenced;
}
}
}

View File

@@ -1,22 +0,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.
-->
<body>
<p>Concrete implementations of commons-logging wrapper APIs.</p>
</body>

View File

@@ -1,255 +0,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.
-->
<body>
<p>Simple wrapper API around multiple logging APIs.</p>
<h3>Overview</h3>
<p>This package provides an API for logging in server-based applications that
can be used around a variety of different logging implementations, including
prebuilt support for the following:</p>
<ul>
<li><a href="http://logging.apache.org/log4j/">Log4J</a> (version 1.2 or later)
from Apache's Logging project. Each named <a href="Log.html">Log</a>
instance is connected to a corresponding Log4J Logger.</li>
<li><a href="http://java.sun.com/j2se/1.4/docs/guide/util/logging/index.html">
JDK Logging API</a>, included in JDK 1.4 or later systems. Each named
<a href="Log.html">Log</a> instance is connected to a corresponding
<code>java.util.logging.Logger</code> instance.</li>
<li><a href="http://avalon.apache.org/logkit/">LogKit</a> from Apache's
Avalon project. Each named <a href="Log.html">Log</a> instance is
connected to a corresponding LogKit <code>Logger</code>.</li>
<li><a href="impl/NoOpLog.html">NoOpLog</a> implementation that simply swallows
all log output, for all named <a href="Log.html">Log</a> instances.</li>
<li><a href="impl/SimpleLog.html">SimpleLog</a> implementation that writes all
log output, for all named <a href="Log.html">Log</a> instances, to
System.err.</li>
</ul>
<h3>Quick Start Guide</h3>
<p>For those impatient to just get on with it, the following example
illustrates the typical declaration and use of a logger that is named (by
convention) after the calling class:
<pre>
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
public class Foo {
private Log log = LogFactory.getLog(Foo.class);
public void foo() {
...
try {
if (log.isDebugEnabled()) {
log.debug("About to do something to object " + name);
}
name.bar();
} catch (IllegalStateException e) {
log.error("Something bad happened to " + name, e);
}
...
}
</pre>
<p>Unless you configure things differently, all log output will be written
to System.err. Therefore, you really will want to review the remainder of
this page in order to understand how to configure logging for your
application.</p>
<h3>Configuring the Commons Logging Package</h3>
<h4>Choosing a <code>LogFactory</code> Implementation</h4>
<p>From an application perspective, the first requirement is to retrieve an
object reference to the <code>LogFactory</code> instance that will be used
to create <code><a href="Log.html">Log</a></code> instances for this
application. This is normally accomplished by calling the static
<code>getFactory()</code> method. This method implements the following
discovery algorithm to select the name of the <code>LogFactory</code>
implementation class this application wants to use:</p>
<ul>
<li>Check for a system property named
<code>org.apache.commons.logging.LogFactory</code>.</li>
<li>Use the JDK 1.3 JAR Services Discovery mechanism (see
<a href="http://java.sun.com/j2se/1.3/docs/guide/jar/jar.html">
http://java.sun.com/j2se/1.3/docs/guide/jar/jar.html</a> for
more information) to look for a resource named
<code>META-INF/services/org.apache.commons.logging.LogFactory</code>
whose first line is assumed to contain the desired class name.</li>
<li>Look for a properties file named <code>commons-logging.properties</code>
visible in the application class path, with a property named
<code>org.apache.commons.logging.LogFactory</code> defining the
desired implementation class name.</li>
<li>Fall back to a default implementation, which is described
further below.</li>
</ul>
<p>If a <code>commons-logging.properties</code> file is found, all of the
properties defined there are also used to set configuration attributes on
the instantiated <code>LogFactory</code> instance.</p>
<p>Once an implementation class name is selected, the corresponding class is
loaded from the current Thread context class loader (if there is one), or
from the class loader that loaded the <code>LogFactory</code> class itself
otherwise. This allows a copy of <code>commons-logging.jar</code> to be
shared in a multiple class loader environment (such as a servlet container),
but still allow each web application to provide its own <code>LogFactory</code>
implementation, if it so desires. An instance of this class will then be
created, and cached per class loader.
<h4>The Default <code>LogFactory</code> Implementation</h4>
<p>The Logging Package APIs include a default <code>LogFactory</code>
implementation class (<a href="impl/LogFactoryImpl.html">
org.apache.commons.logging.impl.LogFactoryImpl</a>) that is selected if no
other implementation class name can be discovered. Its primary purpose is
to create (as necessary) and return <a href="Log.html">Log</a> instances
in response to calls to the <code>getInstance()</code> method. The default
implementation uses the following rules:</p>
<ul>
<li>At most one <code>Log</code> instance of the same name will be created.
Subsequent <code>getInstance()</code> calls to the same
<code>LogFactory</code> instance, with the same name or <code>Class</code>
parameter, will return the same <code>Log</code> instance.</li>
<li>When a new <code>Log</code> instance must be created, the default
<code>LogFactory</code> implementation uses the following discovery
process:
<ul>
<li>Look for a configuration attribute of this factory named
<code>org.apache.commons.logging.Log</code> (for backwards
compatibility to pre-1.0 versions of this API, an attribute
<code>org.apache.commons.logging.log</code> is also consulted).</li>
<li>Look for a system property named
<code>org.apache.commons.logging.Log</code> (for backwards
compatibility to pre-1.0 versions of this API, a system property
<code>org.apache.commons.logging.log</code> is also consulted).</li>
<li>If the Log4J logging system is available in the application
class path, use the corresponding wrapper class
(<a href="impl/Log4JLogger.html">Log4JLogger</a>).</li>
<li>If the application is executing on a JDK 1.4 system, use
the corresponding wrapper class
(<a href="impl/Jdk14Logger.html">Jdk14Logger</a>).</li>
<li>Fall back to the default simple logging implementation
(<a href="impl/SimpleLog.html">SimpleLog</a>).</li>
</ul></li>
<li>Load the class of the specified name from the thread context class
loader (if any), or from the class loader that loaded the
<code>LogFactory</code> class otherwise.</li>
<li>Instantiate an instance of the selected <code>Log</code>
implementation class, passing the specified name as the single
argument to its constructor.</li>
</ul>
<p>See the <a href="impl/SimpleLog.html">SimpleLog</a> JavaDocs for detailed
configuration information for this default implementation.</p>
<h4>Configuring the Underlying Logging System</h4>
<p>The basic principle is that the user is totally responsible for the
configuration of the underlying logging system.
Commons-logging should not change the existing configuration.</p>
<p>Each individual <a href="Log.html">Log</a> implementation may
support its own configuration properties. These will be documented in the
class descriptions for the corresponding implementation class.</p>
<p>Finally, some <code>Log</code> implementations (such as the one for Log4J)
require an external configuration file for the entire logging environment.
This file should be prepared in a manner that is specific to the actual logging
technology being used.</p>
<h3>Using the Logging Package APIs</h3>
<p>Use of the Logging Package APIs, from the perspective of an application
component, consists of the following steps:</p>
<ol>
<li>Acquire a reference to an instance of
<a href="Log.html">org.apache.commons.logging.Log</a>, by calling the
factory method
<a href="LogFactory.html#getInstance(java.lang.String)">
LogFactory.getInstance(String name)</a>. Your application can contain
references to multiple loggers that are used for different
purposes. A typical scenario for a server application is to have each
major component of the server use its own Log instance.</li>
<li>Cause messages to be logged (if the corresponding detail level is enabled)
by calling appropriate methods (<code>trace()</code>, <code>debug()</code>,
<code>info()</code>, <code>warn()</code>, <code>error</code>, and
<code>fatal()</code>).</li>
</ol>
<p>For convenience, <code>LogFactory</code> also offers a static method
<code>getLog()</code> that combines the typical two-step pattern:</p>
<pre>
Log log = LogFactory.getFactory().getInstance(Foo.class);
</pre>
<p>into a single method call:</p>
<pre>
Log log = LogFactory.getLog(Foo.class);
</pre>
<p>For example, you might use the following technique to initialize and
use a <a href="Log.html">Log</a> instance in an application component:</p>
<pre>
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
public class MyComponent {
protected Log log =
LogFactory.getLog(MyComponent.class);
// Called once at startup time
public void start() {
...
log.info("MyComponent started");
...
}
// Called once at shutdown time
public void stop() {
...
log.info("MyComponent stopped");
...
}
// Called repeatedly to process a particular argument value
// which you want logged if debugging is enabled
public void process(String value) {
...
// Do the string concatenation only if logging is enabled
if (log.isDebugEnabled())
log.debug("MyComponent processing " + value);
...
}
}
</pre>
</body>

View File

@@ -1,55 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a artwork.
*
* Defines a single piece of artwork.
*
* Artwork is always associated with an individual track.
* To add a piece of artwork to a track, use IITTrack::AddArtworkFromFile().
* The IITTrack::Artwork property
*
* To get a collection of artwork associated with a track call
* <code>ITTrack.getArtwork()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITArtwork extends ITObject {
public ITArtwork (Dispatch d) {
super(d);
}
/**
* Delete this object.
*/
public void delete() {
Dispatch.call(object, "Delete");
}
/**
* Returns the kind of the object.
* @return Returns the kind of the object.
*/
public ITArtworkFormat getFormat() {
return ITArtworkFormat.values()[Dispatch.get(object, "Format").getInt()];
}
// TODO: Comments
public boolean getIsDownloadedArtwork() {
return Dispatch.get(object, "IsDownloadedArtwork").getBoolean();
}
public String getDescription() {
return Dispatch.get(object, "Description").getString();
}
public void SaveArtworkToFile(String filePath) {
Dispatch.call(object, "SaveArtworkToFile",filePath);
}
}

View File

@@ -1,55 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a collection of Artwork objects.
*
* Note that collection indices are always 1-based.
*
* You can retrieve all the Artworks defined for a source using
* <code>ITSource.getArtwork()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITArtworkCollection {
protected Dispatch object;
public ITArtworkCollection(Dispatch d) {
object = d;
}
/**
* Returns the number of playlists in the collection.
* @return Returns the number of playlists in the collection.
*/
public int getCount() {
return Dispatch.get(object, "Count").getInt();
}
/**
* Returns an ITArtwork object corresponding to the given index (1-based).
* @param index Index of the playlist to retrieve, must be less than or
* equal to <code>ITArtworkCollection.getCount()</code>.
* @return Returns an ITArtwork object corresponding to the given index.
* Will be set to NULL if no playlist could be retrieved.
*/
public ITArtwork getItem (int index) {
Dispatch item = Dispatch.call(object, "Item", index).toDispatch();
return new ITArtwork(item);
}
/**
* Returns an ITArtwork object with the specified persistent ID. See the
* documentation on ITObject for more information on persistent IDs.
* @param highID The high 32 bits of the 64-bit persistent ID.
* @param lowID The low 32 bits of the 64-bit persistent ID.
* @return Returns an ITArtwork object with the specified persistent ID.
* Will be set to NULL if no playlist could be retrieved.
*/
public ITArtwork getItemByPersistentID (int highID, int lowID) {
Dispatch item = Dispatch.call(object, "ItemByPersistentID", highID, lowID).toDispatch();
return new ITArtwork(item);
}
}

View File

@@ -1,13 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the Artwork kind.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITArtworkFormat {
ITArtworkFormatUnknown,
ITArtworkFormatJPEG,
ITArtworkFormatPNG,
ITArtworkFormatBMP;
}

View File

@@ -1,76 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents an audio CD playlist.
*
* An audio CD playlist is always associated with an IITSource of kind
* ITSourceKindAudioCD.
*
* You can retrieve all the playlists defined for a source using
* <code>ITSource.getPlaylists()</code>.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITAudioCDPlaylist extends ITPlaylist {
public ITAudioCDPlaylist(Dispatch d) {
super(d);
}
/**
* Returns the audio CD's artist.
* @return Returns the audio CD's artist.
*/
public String getArtist() {
return Dispatch.get(object, "Artist").getString();
}
/**
* Returns true if this audio CD is a compilation album.
* @return Returns true if this audio CD is a compilation album.
*/
public boolean isCompilation() {
return Dispatch.get(object, "Compilation").getBoolean();
}
/**
* Returns the audio CD's composer.
* @return Returns the audio CD's composer.
*/
public String getComposer() {
return Dispatch.get(object, "Composer").getString();
}
/**
* Returns the total number of discs in this CD's album.
* @return Returns the total number of discs in this CD's album.
*/
public long getDiscCount() {
return Dispatch.get(object, "DiscCount").getLong();
}
/**
* Returns the index of the CD disc in the source album.
* @return Returns the index of the CD disc in the source album.
*/
public long getDiscNumber() {
return Dispatch.get(object, "DiscNumber").getLong();
}
/**
* Returns the audio CD's genre.
* @return Returns the audio CD's genre.
*/
public String getGenre() {
return Dispatch.get(object, "Genre").getString();
}
/**
* Reveals the CD playlist in the main browser window.
*/
public void reveal() {
Dispatch.call(object, "Reveal");
}
}

View File

@@ -1,45 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents the main browser window.
*
* You can retrieve the main browser window using
* <code>iTunes.BrowserWindow()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITBrowserWindow extends ITWindow {
public ITBrowserWindow (Dispatch d) {
super(d);
}
/**
* Returns the kind of the object.
* @return Returns the kind of the object.
*/
public boolean getMiniPlayer() {
return Dispatch.get(object, "MiniPlayer").getBoolean();
}
// TODO: Comments
public ITTrackCollection getSelectedTracks() {
Dispatch collection = Dispatch.call(object, "SelectedTracks").getDispatch();
return new ITTrackCollection(collection);
}
public ITPlaylist getSelectedPlaylist() {
Dispatch playlist = Dispatch.get(object, "SelectedPlaylist").toDispatch();
return new ITPlaylist(playlist);
}
public void setSelectedPlaylist(ITPlaylist playlist) {
Dispatch dispatchRef = playlist.fetchDispatch();
Dispatch.put(object, "SelectedPlaylist", dispatchRef);
}
}

View File

@@ -1,12 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the reason the COM interface is being disabled.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITCOMDisabledReason {
ITCOMDisabledReasonOther,
ITCOMDisabledReasonDialog,
ITCOMDisabledReasonQuitting;
}

View File

@@ -1,236 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents an equalizer preset.
* You can retrieve or set the currently selected EQ preset using the
* <code>iTunes.getCurrentEQPreset()<code> method.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITEQPreset {
protected Dispatch object;
public ITEQPreset(Dispatch d) {
object = d;
}
/**
* Returns the name of the EQ Preset (e.g. "Acoustic").
* @return Returns the name of the EQ Preset (e.g. "Acoustic").
*/
public String getName() {
return Dispatch.get(object, "Name").getString();
}
/**
* Returns true if the EQ preset can be modified.
* @return True if the EQ preset can be modified.
*/
public boolean getModifiable() {
return Dispatch.get(object, "Modifiable").getBoolean();
}
/**
* Set the equalizer preamp level (-12.0 db to +12.0 db).
* @param level The new equalizer preamp level (-12.0 db to +12.0 db).
*/
public void setPreamp(double level) {
Dispatch.put(object, "Preamp", level);
}
/**
* Returns the equalizer preamp level (-12.0db to +12.0db).
* @return Returns the equalizer preamp level (-12.0db to +12.0db).
*/
public double getPreamp() {
return Dispatch.get(object, "Preamp").getDouble();
}
/**
* Set the equalizer 32Hz level (-12.0 db to +12.0 db).
* @param level The new equalizer 32Hz level (-12.0 db to +12.0db).
*/
public void setBand1(double level) {
Dispatch.put(object, "Band1", level);
}
/**
* Returns the equalizer 32Hz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 32Hz level (-12.0 db to +12.0 db).
*/
public double getBand1() {
return Dispatch.get(object, "Band1").getDouble();
}
/**
* Set the equalizer 64Hz level (-12.0 db to +12.0 db).
* @param level The new equalizer 64Hz level (-12.0 db to +12.0db).
*/
public void setBand2(double level) {
Dispatch.put(object, "Band2", level);
}
/**
* Returns the equalizer 64Hz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 64Hz level (-12.0 db to +12.0 db).
*/
public double getBand2() {
return Dispatch.get(object, "Band2").getDouble();
}
/**
* Set the equalizer 125Hz level (-12.0 db to +12.0 db).
* @param level The new equalizer 125Hz level (-12.0 db to +12.0db).
*/
public void setBand3(double level) {
Dispatch.put(object, "Band3", level);
}
/**
* Returns the equalizer 125Hz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 125Hz level (-12.0 db to +12.0 db).
*/
public double getBand3() {
return Dispatch.get(object, "Band3").getDouble();
}
/**
* Set the equalizer 250Hz level (-12.0 db to +12.0 db).
* @param level The new equalizer 250Hz level (-12.0 db to +12.0db).
*/
public void setBand4(double level) {
Dispatch.put(object, "Band4", level);
}
/**
* Returns the equalizer 250Hz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 250Hz level (-12.0 db to +12.0 db).
*/
public double getBand4() {
return Dispatch.get(object, "Band4").getDouble();
}
/**
* Set the equalizer 500Hz level (-12.0 db to +12.0 db).
* @param level The new equalizer 500Hz level (-12.0 db to +12.0db).
*/
public void setBand5(double level) {
Dispatch.put(object, "Band5", level);
}
/**
* Returns the equalizer 500Hz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 500Hz level (-12.0 db to +12.0 db).
*/
public double getBand5() {
return Dispatch.get(object, "Band5").getDouble();
}
/**
* Set the equalizer 1KHz level (-12.0 db to +12.0 db).
* @param level The new equalizer 1KHz level (-12.0 db to +12.0db).
*/
public void setBand6(double level) {
Dispatch.put(object, "Band6", level);
}
/**
* Returns the equalizer 1KHz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 1KHz level (-12.0 db to +12.0 db).
*/
public double getBand6() {
return Dispatch.get(object, "Band6").getDouble();
}
/**
* Set the equalizer 2KHz level (-12.0 db to +12.0 db).
* @param level The new equalizer 2KHz level (-12.0 db to +12.0db).
*/
public void setBand7(double level) {
Dispatch.put(object, "Band7", level);
}
/**
* Returns the equalizer 2KHz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 2KHz level (-12.0 db to +12.0 db).
*/
public double getBand7() {
return Dispatch.get(object, "Band7").getDouble();
}
/**
* Set the equalizer 4KHz level (-12.0 db to +12.0 db).
* @param level The new equalizer 4KHz level (-12.0 db to +12.0db).
*/
public void setBand8(double level) {
Dispatch.put(object, "Band8", level);
}
/**
* Returns the equalizer 4KHz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 4KHz level (-12.0 db to +12.0 db).
*/
public double getBand8() {
return Dispatch.get(object, "Band8").getDouble();
}
/**
* Set the equalizer 8KHz level (-12.0 db to +12.0 db).
* @param level The new equalizer 8KHz level (-12.0 db to +12.0db).
*/
public void setBand9(double level) {
Dispatch.put(object, "Band9", level);
}
/**
* Returns the equalizer 8KHz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 8KHz level (-12.0 db to +12.0 db).
*/
public double getBand9() {
return Dispatch.get(object, "Band9").getDouble();
}
/**
* Set the equalizer 16KHz level (-12.0 db to +12.0 db).
* @param level The new equalizer 16KHz level (-12.0 db to +12.0db).
*/
public void setBand10(double level) {
Dispatch.put(object, "Band10", level);
}
/**
* Returns the equalizer 16KHz level (-12.0 db to +12.0 db).
* @return Returns the equalizer 16KHz level (-12.0 db to +12.0 db).
*/
public double getBand10() {
return Dispatch.get(object, "Band10").getDouble();
}
/**
* Delete this EQ Preset.
* Any EQ preset can be deleted, including built-in presets, except for the
* Manual preset.
* @param updateAllTracks If true, any tracks that use this EQ preet will be
* set to have no assigned EQ preset.
*/
public void delete(boolean updateAllTracks) {
Dispatch.call(object, "Delete", updateAllTracks);
}
/**
* Rename this EQ Preset.
* The name of any EQ preset can be changed, including built-in presets,
* except for the Manual preset.
* EQ preset names cannot start with leading spaces. If you specify a name
* that starts with leading spaces they will be stripped out.
* @param updateAllTracks If true, any tracks that use this EQ preet will be
* updated with the new preset name.
*/
public void rename(String newName, boolean updateAllTracks) {
Dispatch.call(object, "Rename", newName, updateAllTracks);
}
}

View File

@@ -1,39 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a file or CD track.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITFileOrCDTrack extends ITTrack {
public ITFileOrCDTrack (Dispatch d) {
super(d);
}
/**
* Reveals the track in the main browser window.
*/
public void reveal() {
Dispatch.call(object, "Reveal");
}
public ITVideoKind getVideoKind() {
return ITVideoKind.values()[Dispatch.get(object, "VideoKind").getInt()];
}
public ITRatingKind getRatingKind() {
return ITRatingKind.values()[Dispatch.get(object, "RatingKind").getInt()];
}
public String getLocation() {
return Dispatch.get(object, "Location").getString();
}
public ITArtworkCollection getArtworks() {
Dispatch artworks = Dispatch.get(object, "Artwork").toDispatch();
return new ITArtworkCollection(artworks);
}
}

View File

@@ -1,20 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a library playlist.
*
* A library playlist consists of all the tracks in a user's library.
*
* For convenience, you can retrieve the main library playlist using
* <code>iTunes.getLibraryPlaylist()</code>.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITLibraryPlaylist extends ITPlaylist {
public ITLibraryPlaylist(Dispatch d) {
super(d);
}
}

View File

@@ -1,112 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Defines a source, playlist or track.
*
* An ITObject uniquely identifies a source, playlist, or track in iTunes using
* four separate IDs. These are runtime IDs, they are only valid while the
* current instance of iTunes is running.
*
* As of iTunes 7.7, you can also identify an ITObject using a 64-bit persistent
* ID, which is valid across multiple invocations of iTunes.
*
* The main use of the ITObject interface is to allow clients to track iTunes
* database changes using
* <code>iTunesEventsInterface.onDatabaseChangedEvent()</code>.
*
* You can retrieve an ITObject with a specified runtime ID using
* <code>iTunes.getITObjectByID()</code>.
*
* An ITObject will always have a valid, non-zero source ID.
*
* An ITObject corresponding to a playlist or track will always have a valid
* playlist ID. The playlist ID will be zero for a source.
*
* An ITObject corresponding to a track will always have a valid track and
* track database ID. These IDs will be zero for a source or playlist.
*
* A track ID is unique within the track's playlist. A track database ID is
* unique across all playlists. For example, if the same music file is in two
* different playlists, each of the tracks could have different track IDs, but
* they will have the same track database ID.
*
* An ITObject also has a 64-bit persistent ID which can be used to identify
* the ITObject across multiple invocations of iTunes.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITObject {
protected Dispatch object;
public ITObject(Dispatch d) {
object = d;
}
/**
* Returns the JACOB Dispatch object for this object.
* @return Returns the JACOB Dispatch object for this object.
*/
public Dispatch fetchDispatch() {
return object;
}
/**
* Set the name of the object.
* @param name The new name of the object.
*/
public void setName (String name) {
Dispatch.put(object, "Name", name);
}
/**
* Returns the name of the object.
* @return Returns the name of the object.
*/
public String getName() {
return Dispatch.get(object, "Name").getString();
}
/**
* Returns the index of the object in internal application order.
* @return The index of the object in internal application order.
*/
public int getIndex() {
return Dispatch.get(object, "Index").getInt();
}
/**
* Returns the ID that identifies the source.
* @return Returns the ID that identifies the source.
*/
public int getSourceID() {
return Dispatch.get(object, "SourceID").getInt();
}
/**
* Returns the ID that identifies the playlist.
* @return Returns the ID that identifies the playlist.
*/
public int getPlaylistID() {
return Dispatch.get(object, "PlaylistID").getInt();
}
/**
* Returns the ID that identifies the track within the playlist.
* @return Returns the ID that identifies the track within the playlist.
*/
public int getTrackID() {
return Dispatch.get(object, "TrackID").getInt();
}
/**
* Returns the ID that identifies the track, independent of its playlist.
* @return Returns the ID that identifies the track, independent of its playlist.
*/
public int getTrackDatabaseID() {
return Dispatch.get(object, "TrackDatabaseID").getInt();
}
}

View File

@@ -1,53 +0,0 @@
package com.dt.iTunesController;
/**
* Simple utility wrapper class to represent the persistent object identity
* ID numbers. Use the getHigh() and getLow() methods individually to get
* each ID, or the combined hex string through toString().
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITObjectPersistentID {
private long High;
private long Low;
private String hexString;
/**
* Create the ITObjectPersistentID. This class is not intended to be created
* manually, and this function should only be used by classes implementing
* this utility.
* @param high The High Persistent ID
* @param low The Low Persistent ID
*/
public ITObjectPersistentID(long high, long low) {
this.High=high;
this.Low=low;
this.hexString = String.format("%8s%8s",Long.toHexString(this.High),Long.toHexString(this.Low)).toUpperCase().replace(' ','0');
}
/**
* Returns the high persistent ID.
* @return The high persistent ID.
*/
public long getHigh() {
return this.High;
}
/**
* Returns the low persistent ID.
* @return The low persistent ID.
*/
public long getLow() {
return this.Low;
}
/**
* Return a string representation (in hex) of the persistent IDs.
* @return String representation of the persistent IDs.
*/
public String toString() {
return this.hexString;
}
}

View File

@@ -1,62 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents the status of an asynchronous add or convert operation.
*
* When a track is added using TLibraryPlaylist.addFile(),
* ITLibraryPlaylist.AddFiles(), IITUserPlaylist.addFile(), or
* ITUserPlaylist.addFiles(), the add may not complete immediately if iTunes
* needs to make a copy of the file.
*
* Similarly, when converting or importing a file or track using
* <code>iTunes.convertFile()</code>, <code>iTunes.convertFiles()</code>,
* <code>iTunes.convertTrack()</code> or <code>iTunes.convertTracks()</code>,
* the conversion will never complete immediately.
*
* These methods return an <code>ITOperationStatus</code> object, which can be
* polled todetermine when the operation is done. This object will also return
* the collection of newly added or converted tracks.
*
* As of version 1.1 of the iTunes type library, you should use
* <code>iTunes.convertFile2()</code>, <code>iTunes.convertFiles2()</code>,
* <code>iTunes.convertTrack2()</code> or <code>iTunes.convertTracks2()</code>
* instead of the original convert methods. These new methods return an
* <code>ITConvertOperationStatus</code> object to allow clients to retrieve
* additional conversion progress information.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITOperationStatus {
protected Dispatch object;
public ITOperationStatus(Dispatch d) {
object = d;
}
/**
* Returns true if the operation is still in progress.
* You cannot retrieve the <code>ITOperationStatus.getTracks()</code>
* property until the operation completes.
* @return Returns true if the operation is still in progress.
*/
public boolean getInProgress() {
return Dispatch.get(object, "InProgress").getBoolean();
}
/**
* Returns a collection containing the tracks that were generated by the
* operation.
* You cannot retrieve this property until
* <code>ITOperationStatus.getInProgress()</code> returns false
* @return Returns a collection containing the tracks that were generated by
* the operation.
*/
public ITTrackCollection getTracks() {
Dispatch tracks = Dispatch.get(object, "Tracks").toDispatch();
return new ITTrackCollection(tracks);
}
}

View File

@@ -1,13 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the state of the player.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITPlayerState {
ITPlayerStateStopped,
ITPlayerStatePlaying,
ITPlayerStateFastForward,
ITPlayerStateRewind;
}

View File

@@ -1,154 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a playlist.
*
* A playlist is always associated with an ITSource.
*
* You can retrieve all the playlists defined for a source using
* <code>ITSource.getPlaylists()</code>.
*
* For convenience, you can retrieve the main library playlist using
* <code>iTunes.getLibraryPlaylist()</code>.
*
* You can create a new playlist using <code>iTunes.createPlaylist()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITPlaylist extends ITObject {
public ITPlaylist (Dispatch d) {
super(d);
}
/**
* Delete this object.
*/
public void delete() {
Dispatch.call(object, "Delete");
}
/**
* Start playing the first track in this object.
*/
public void playFirstTrack() {
Dispatch.call(object, "PlayFirstTrack");
}
/**
* Print this object.
* @param showPrintDialog If true, display the print dialog.
* @param printKind The printout kind.
* @param theme The name of the theme to use. This corresponds to the name
* of a Theme combo box item in the print dialog for the specified printKind
* (e.g. "Track length"). This string cannot be longer than 255 characters,
* but it may be empty.
*/
public void print(boolean showPrintDialog, ITPlaylistPrintKind printKind, String theme) {
Dispatch.call(object, "Print", showPrintDialog, printKind.ordinal(), theme);
}
/**
* Returns a collection containing the tracks with the specified text.
* @param searchText The text to search for. This string cannot be longer
* than 255 chracters.
* @param searchFields Specifies which fields of each track should be
* searched for searchText.
* @return Collection of IITTrack objects. This will be NULL if no tracks
* meet the search criteria.
*/
public ITTrackCollection search (String searchText, ITPlaylistSearchField searchFields) {
Dispatch collection = Dispatch.call(object, "Search", searchText, searchFields.ordinal()).getDispatch();
return new ITTrackCollection(collection);
}
/**
* Returns the kind of the object.
* @return Returns the kind of the object.
*/
public ITPlaylistKind getKind() {
return ITPlaylistKind.values()[Dispatch.get(object, "Kind").getInt()];
}
/**
* Returns an ITSource object corresponding to the source that contains the
* object.
* @return Returns an ITSource object corresponding to the source that
* contains the object.
*/
public ITSource getSource() {
Dispatch source = Dispatch.get(object, "Source").toDispatch();
return new ITSource(source);
}
/**
* Returns the total length of all songs in the object (in seconds).
* @return Returns the total length of all songs in the object (in
* seconds).
*/
public int getDuration() {
return Dispatch.get(object, "Duration").getInt();
}
/**
* Set whether songs in the object should be played in random order.
* @param shouldShuffle True if songs in the object should be played in
* random order.
*/
public void setShuffle(boolean shouldShuffle) {
Dispatch.put(object, "Shuffle", shouldShuffle);
}
/**
* Returns the total size of all songs in the object (in bytes).
* @return Returns the total size of all songs in the object (in bytes).
*/
public double getSize() {
return Dispatch.get(object, "Size").getDouble();
}
/**
* Sets the playback repeat mode.
* @param repeatMode The new playback repeat mode.
*/
public void setSongRepeat(ITPlaylistRepeatMode repeatMode) {
Dispatch.put(object, "SongRepeat", repeatMode.ordinal());
}
/**
* Returns the playback repeat mode.
* @return Returns the playback repeat mode.
*/
public ITPlaylistRepeatMode getSongRepeat() {
return ITPlaylistRepeatMode.values()[Dispatch.get(object, "SongRepeat").getInt()];
}
/**
* Returns the total length of all songs in the object (in MM:SS format).
* @return Returns the total length of all songs in the object (in
* MM:SS format).
*/
public String getTime() {
return Dispatch.get(object, "Time").getString();
}
/**
* Returns true if the object is visible in the sources list.
* @return True if the object is visible in the sources list.
*/
public boolean getVisible() {
return Dispatch.get(object, "Visible").getBoolean();
}
/**
* Returns a collection containing the tracks in this object.
* @return Collection of ITTrack objects.
*/
public ITTrackCollection getTracks() {
Dispatch tracks = Dispatch.get(object, "Tracks").toDispatch();
return new ITTrackCollection(tracks);
}
}

View File

@@ -1,67 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a collection of playlist objects.
*
* Note that collection indices are always 1-based.
*
* You can retrieve all the playlists defined for a source using
* <code>ITSource.getPlaylists()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITPlaylistCollection {
protected Dispatch object;
public ITPlaylistCollection(Dispatch d) {
object = d;
}
/**
* Returns the number of playlists in the collection.
* @return Returns the number of playlists in the collection.
*/
public int getCount() {
return Dispatch.get(object, "Count").getInt();
}
/**
* Returns an ITPlaylist object corresponding to the given index (1-based).
* @param index Index of the playlist to retrieve, must be less than or
* equal to <code>ITPlaylistCollection.getCount()</code>.
* @return Returns an ITPlaylist object corresponding to the given index.
* Will be set to NULL if no playlist could be retrieved.
*/
public ITPlaylist getItem (int index) {
Dispatch item = Dispatch.call(object, "Item", index).toDispatch();
return new ITPlaylist(item);
}
/**
* Returns an ITPlaylist object withthe specified name.
* @param name The name of the playlist to retrieve.
* @return Returns an ITPlaylist object corresponding to the given index.
* Will be set to NULL if no playlist could be retrieved.
*/
public ITPlaylist ItemByName (String name) {
Dispatch item = Dispatch.call(object, "ItemByName", name).toDispatch();
return new ITPlaylist(item);
}
/**
* Returns an ITPlaylist object with the specified persistent ID. See the
* documentation on ITObject for more information on persistent IDs.
* @param highID The high 32 bits of the 64-bit persistent ID.
* @param lowID The low 32 bits of the 64-bit persistent ID.
* @return Returns an ITPlaylist object with the specified persistent ID.
* Will be set to NULL if no playlist could be retrieved.
*/
public ITPlaylist getItemByPersistentID (int highID, int lowID) {
Dispatch item = Dispatch.call(object, "ItemByPersistentID", highID, lowID).toDispatch();
return new ITPlaylist(item);
}
}

View File

@@ -1,15 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the playlist kind.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITPlaylistKind {
ITPlaylistKindUnknown,
ITPlaylistKindLibrary,
ITPlaylistKindUser,
ITPlaylistKindCD,
ITPlaylistKindDevice,
ITPlaylistKindRadioTuner;
}

View File

@@ -1,14 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the kind of playlist printout.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITPlaylistPrintKind {
ITPlaylistPrintKindPlaylist,
ITPlaylistPrintKindAlbumlist,
ITPlaylistPrintKindInsert;
}

View File

@@ -1,14 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the playlist playback repeat mode.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITPlaylistRepeatMode {
ITPlaylistRepeatModeOff,
ITPlaylistRepeatModeOne,
ITPlaylistRepeatModeAll;
}

View File

@@ -1,16 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the fields in each track that will be searched by
* <code>ITPlaylist.search()</code>.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITPlaylistSearchField {
ITPlaylistSearchFieldAll,
ITPlaylistSearchFieldVisible,
ITPlaylistSearchFieldArtists,
ITPlaylistSearchFieldAlbums,
ITPlaylistSearchFieldComposers,
ITPlaylistSearchFieldSongNames;
}

View File

@@ -1,11 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the rating kind.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITRatingKind {
ITRatingKindUser,
ITRatingKindComputed;
}

View File

@@ -1,51 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents an entry in the Source list (music library, CD, device, etc.).
* You can retrieve all the sources using <code>iTunes.getSources()</code>.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITSource extends ITObject {
public ITSource(Dispatch d) {
super(d);
}
/**
* Returns the kind of the source.
* @return Returns the kind of the source.
*/
public ITSourceKind getKind() {
return ITSourceKind.values()[Dispatch.get(object, "Kind").getInt()];
}
/**
* Returns the total size of the source, if it has a fixed size.
* @return Returns the total size of the source, if it has a fixed size.
*/
public double getCapacity() {
return Dispatch.get(object, "Capacity").getDouble();
}
/**
* Returns the free space on the source, if it has a fixed size.
* @return Returns the free space on the source, if it has a fixed size.
*/
public double getFreespace() {
return Dispatch.get(object, "Freespace").getDouble();
}
/**
* Returns a collection containing the playlists in this source.
* The source's primary playlist is always the first playlist in the
* collection.
* @return Collection of IITPlaylist objects.
*/
public ITPlaylistCollection getPlaylists() {
Dispatch playlists = Dispatch.get(object, "Playlists").toDispatch();
return new ITPlaylistCollection(playlists);
}
}

View File

@@ -1,66 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a collection of source objects.
*
* Note that collection indices are always 1-based.
*
* You can retrieve all the sources using <code>ITSource.getSources()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITSourceCollection {
protected Dispatch object;
public ITSourceCollection(Dispatch d) {
object = d;
}
/**
* Returns the number of sources in the collection.
* @return Returns the number of sources in the collection.
*/
public int getCount() {
return Dispatch.get(object, "Count").getInt();
}
/**
* Returns an ITSource object corresponding to the given index (1-based).
* @param index Index of the source to retrieve, must be less than or
* equal to <code>ITSourceCollection.getCount()</code>.
* @return Returns an ITSource object corresponding to the given index.
* Will be set to NULL if no source could be retrieved.
*/
public ITSource getItem (int index) {
Dispatch item = Dispatch.call(object, "Item", index).toDispatch();
return new ITSource(item);
}
/**
* Returns an ITSource object withthe specified name.
* @param name The name of the source to retrieve.
* @return Returns an ITSource object corresponding to the given index.
* Will be set to NULL if no source could be retrieved.
*/
public ITSource getItemByName (String name) {
Dispatch item = Dispatch.call(object, "ItemByName", name).toDispatch();
return new ITSource(item);
}
/**
* Returns an ITSource object with the specified persistent ID. See the
* documentation on ITObject for more information on persistent IDs.
* @param highID The high 32 bits of the 64-bit persistent ID.
* @param lowID The low 32 bits of the 64-bit persistent ID.
* @return Returns an ITSource object with the specified persistent ID.
* Will be set to NULL if no source could be retrieved.
*/
public ITSource getItemByPersistentID (int highID, int lowID) {
Dispatch item = Dispatch.call(object, "ItemByPersistentID", highID, lowID).toDispatch();
return new ITSource(item);
}
}

View File

@@ -1,17 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the source kind.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITSourceKind {
ITSourceKindUnknown,
ITSourceKindLibrary,
ITSourceKindIPod,
ITSourceKindAudioCD,
ITSourceKindMP3CD,
ITSourceKindDevice,
ITSourceKindRadioTuner,
ITSourceKindSharedLibrary;
}

View File

@@ -1,492 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.*;
import java.util.Date;
/**
* Represents a track.
*
* A track represents a song in a single playlist. A song may be in more than
* one playlist, in which case it would be represented by multiple tracks.
*
* You can retrieve the currently targeted (playing) track using
* <code>iTunes.getCurrentTrack()</code>.
*
* Typically, an ITrack is accessed through an ITTrackCollection.
*
* You can retrieve all the tracks defined for a playlist using
* <code>ITPlaylist.getTracks()</code>.
*
* You can retrieve the currently selected track or tracks using
* <code>iTunes.getSelectedTracks()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITTrack extends ITObject {
public ITTrack (Dispatch d) {
super(d);
}
/**
* Delete this object.
*/
public void delete() {
Dispatch.call(object, "Delete");
}
/**
* Start playing this object.
*/
public void play() {
Dispatch.call(object, "Play");
}
/**
* Set the name of the album containing the object.;
* @param album The new name of the album containing the object.
*/
public void setAlbum(String album) {
Dispatch.put(object, "Album", album);
}
/**
* Returns the name of the album containing the object.
* @return Returns the name of the album containing the object.
*/
public String getAlbum() {
return Dispatch.get(object, "Album").getString();
}
/**
* Set the name of the artist/source of the object.
* @param artist The new artist/source of the object.
*/
public void setArtist(String artist) {
Dispatch.put(object, "Artist", artist);
}
/**
* Returns the name of the artist/source of the object.
* @return Returns the name of the artist/source of the object.
*/
public String getArtist() {
return Dispatch.get(object, "Artist").getString();
}
/**
* Returns the bit rate of the object (in kbps).
* @return Returns the bit rate of the object (in kbps).
*/
public int getBitRate() {
return Dispatch.get(object, "BitRate").getInt();
}
/**
* Set the tempo of the object (in beats per minute).
* @param beatsPerMinute The new tempo of the object (in beats per minute).
*/
public void setBPM(int beatsPerMinute) {
Dispatch.put(object, "BPM", beatsPerMinute);
}
/**
* Returns the tempo of the object (in beats per minute).
* @return Returns the tempo of the object (in beats per minute).
*/
public int getBPM() {
return Dispatch.get(object, "BPM").getInt();
}
/**
* Set freeform notes about the object.
* @param comment The new freeform notes about the object.
*/
public void setComment(String comment) {
Dispatch.put(object, "Comment", comment);
}
/**
* Returns freeform notes about the object.
* @return Returns freeform notes about the object.
*/
public String getComment() {
return Dispatch.get(object, "Comment").getString();
}
/**
* Set whether this object is from a compilation album.
* @param isCompilation True if this object should be from a compilation album.
*/
public void setCompilation(boolean isCompilation) {
Dispatch.put(object, "Compilation", isCompilation);
}
/**
* Returns true if this object is from a compilation album.
* @return Returns true if this object is from a compilation album.
*/
public boolean getCompilation() {
return Dispatch.get(object, "Compilation").getBoolean();
}
/**
* Set the composer of the object.
* @param composer The new composer of the object.
*/
public void setComposer (String composer) {
Dispatch.put(object, "Composer", composer);
}
/**
* Returns the composer of the object.
* @return Returns the composer of the object.
*/
public String getComposer() {
return Dispatch.get(object, "Composer").getString();
}
/**
* Returns the date the object was added to the playlist.
* @return Returns the date the object was added to the playlist.
*/
public Date getDateAdded() {
return Dispatch.get(object, "DateAdded").getJavaDate();
}
/**
* Set the total number of discs in the source album.
* @param discCount The new total number of discs in the source album.
*/
public void setDiscCount (int discCount) {
Dispatch.put(object, "DiscCount", discCount);
}
/**
* Returns the total number of discs in the source album.
* @return Returns the total number of discs in the source album.
*/
public int getDiscCount() {
return Dispatch.get(object, "DiscCount").getInt();
}
/**
* Set the index of the disc containing the object on the source album.
* @param discNumber The new index of the disc containing the object on the
* source album.
*/
public void setDiscNumber (int discNumber) {
Dispatch.put(object, "DiscNumber", discNumber);
}
/**
* Returns the index of the disc containing the object on the source album.
* @return Returns the index of the disc containing the object on the source
* album.
*/
public int getDiscNumber() {
return Dispatch.get(object, "DiscNumber").getInt();
}
/**
* Returns the length of the object (in seconds).
* @return Returns the length of the object (in seconds).
*/
public int getDuration() {
return Dispatch.get(object, "Duration").getInt();
}
/**
* Set whether this object is checked for playback.
* @param shouldBeEnabled True if the object should be checked for playback.
*/
public void setEnabled (boolean shouldBeEnabled) {
Dispatch.put(object, "Enabled", shouldBeEnabled);
}
/**
* Returns true if the object is checked for playback.
* @return Returns true if the object is checked for playback.
*/
public boolean getEnabled() {
return Dispatch.get(object, "Enabled").getBoolean();
}
/**
* Set the name of the EQ preset of the object.
* @param eq The new name of the EQ preset of the object.
*/
public void setEQ (String eq) {
Dispatch.put(object, "EQ", eq);
}
/**
* Returns the name of the EQ preset of the object.
* @return Returns the name of the EQ preset of the object.
*/
public String getEQ() {
return Dispatch.get(object, "EQ").getString();
}
/**
* Set the stop time of the object (in seconds).
* @param finish The new stop time of the object (in seconds).
*/
public void setFinish(int finish) {
Dispatch.put(object, "Finish", finish);
}
/**
* Returns the stop time of the object (in seconds).
* @return Returns the stop time of the object (in seconds).
*/
public int getFinish() {
return Dispatch.get(object, "Finish").getInt();
}
/**
* Returns the music/audio genre (category) of the object.
* @param genre Returns the music/audio genre (category) of the object.
*/
public void setGenre(String genre) {
Dispatch.put(object, "Genre", genre);
}
/**
* Set the music/audio genre (category) of the object.
* @return The new music/audio genre (category) of the object.
*/
public String getGenre() {
return Dispatch.get(object, "Genre").getString();
}
/**
* Set the grouping (piece) of the object.
* Generally used to denote movements within classical work.
* @param grouping The new grouping (piece) of the object.
*/
public void setGrouping (String grouping) {
Dispatch.put(object, "Grouping", grouping);
}
/**
* Returns the grouping (piece) of the object.
* Generally used to denote movements within classical work.
* @return Returns the grouping (piece) of the object.
*/
public String getGrouping() {
return Dispatch.get(object, "Grouping").getString();
}
public ITTrackKind getKind() {
return ITTrackKind.values()[Dispatch.get(object, "Kind").getInt()];
}
/**
* Returns the text description of the object (e.g. "AAC audio file").
* @return Returns the text description of the object (e.g. "AAC audio file").
*/
public String getKindAsString() {
return Dispatch.get(object, "KindAsString").getString();
}
/**
* Returns the modification date of the content of the object.
* @return Returns the modification date of the content of the object.
*/
public Date getModificationDate() {
return Dispatch.get(object, "ModificationDate").getJavaDate();
}
/**
* Set the number of times the object has been played. This property cannot
* be set if the object is not playable (e.g. a PDF file).
* @param playedCount The new number of times the object has been played.
*/
public void setPlayedCount (int playedCount) {
Dispatch.put(object, "PlayedCount", playedCount);
}
/**
* Returns the number of times the object has been played.
* @return Returns the number of times the object has been played.
*/
public int getPlayedCount() {
return Dispatch.get(object, "PlayedCount").getInt();
}
/**
* Set the date and time the object was last played. This property cannot be
* set if the object is not playable (e.g. a PDF file).
* A value of zero means no played date.
* @param playedDate The new date and time the object was last played.
*/
public void setPlayedDate (Date playedDate) {
Dispatch.put(object, "PlayedDate", playedDate);
}
/**
* Returns the date and time the object was last played.
* A value of zero means no played date.
* @return Returns the date and time the object was last played.
*/
public Date getPlayedDate() {
return Dispatch.get(object, "PlayedDate").getJavaDate();
}
/**
* Returns an ITPlaylist object corresponding to the playlist that contains
* the object. Use ITFileOrCDTrack::Playlists() or IITURLTrack::Playlists()
* to get the collection of all playlists that contain the song this object
* represents.
* @return Returns an ITPlaylist object corresponding to the playlist that
* contains the object.
*/
public ITPlaylist getPlaylist() {
Dispatch playlist = Dispatch.get(object, "Playlist").toDispatch();
return new ITPlaylist(playlist);
}
/**
* Returns the play order index of the object in the owner playlist
* (1-based).
* You can pass this index to IITTrackCollection::ItemByPlayOrder() for the
* collection returned by ITPlaylist::Tracks() to retrieve an ITTrack
* object corresponding to this object.
* @return Returns the play order index of the object in the owner playlist.
*/
public int getPlayOrderIndex() {
return Dispatch.get(object, "PlayOrderIndex").getInt();
}
/**
* Set the rating of the object (0 to 100). If the object rating is set to 0,
* it will be computed based on the album rating.
* @param rating The new rating of the object (0 to 100).
*/
public void setRating (int rating) {
Dispatch.put(object, "Rating", rating);
}
/**
* Returns the rating of the object (0 to 100). If the object rating has never
* been set, or has been set to 0, it will be computed based on the album
* rating.
* @return Returns the rating of the object (0 to 100).
*/
public int getRating() {
return Dispatch.get(object, "Rating").getInt();
}
/**
* Returns the sample rate of the object (in Hz).
* @return Returns the sample rate of the object (in Hz).
*/
public int getSampleRate() {
return Dispatch.get(object, "SampleRate").getInt();
}
/**
* Returns the size of the object (in bytes).
* @return Returns the size of the object (in bytes).
*/
public int getSize() {
return Dispatch.get(object, "Size").getInt();
}
/**
* Set the start time of the object (in seconds).
* @param start The new start time of the object (in seconds).
*/
public void setStart (int start) {
Dispatch.put(object, "Start", start);
}
/**
* Returns the start time of the object (in seconds).
* @return Returns the start time of the object (in seconds).
*/
public int getStart() {
return Dispatch.get(object, "Start").getInt();
}
/**
* Returns the length of the object (in MM:SS format).
* @return Returns the length of the object (in MM:SS format).
*/
public String getTime() {
return Dispatch.get(object, "Time").getString();
}
/**
* Set the total number of tracks on the source album.
* @param trackCount The new total number of tracks on the source album.
*/
public void setTrackCount (int trackCount) {
Dispatch.put(object, "TrackCount", trackCount);
}
/**
* Returns the total number of tracks on the source album.
* @return Returns the total number of tracks on the source album.
*/
public int getTrackCount() {
return Dispatch.get(object, "TrackCount").getInt();
}
/**
* Set the index of the object on the source album.
* @param trackNumber The new index of the object on the source album.
*/
public void setTrackNumber (int trackNumber) {
Dispatch.put(object, "TrackNumber", trackNumber);
}
/**
* Returns the index of the object on the source album.
* @return Returns the index of the object on the source album.
*/
public int getTrackNumber() {
return Dispatch.get(object, "TrackNumebr").getInt();
}
/**
* Set the relative volume adjustment of the object (-100% to 100%).
* @param volumeAdjustment Set the relative volume adjustment of the object
* (-100% to 100%).
*/
public void setVolumeAdjustment (int volumeAdjustment) {
Dispatch.put(object, "VolumeAdjustment", volumeAdjustment);
}
/**
* Returns the relative volume adjustment of the object (-100% to 100%).
* @return Returns the relative volume adjustment of the object (-100% to 100%).
*/
public int getVolumeAdjustment() {
return Dispatch.get(object, "VolumeAdjustment").getInt();
}
/**
* Set the year the object was recorded/released.
* @param year The new year the object was recorded/released.
*/
public void setYear (int year) {
Dispatch.put(object, "Year", year);
}
/**
* Returns the year the object was recorded/released.
* @return Returns the year the object was recorded/released.
*/
public int getYear() {
return Dispatch.get(object, "Year").getInt();
}
public ITArtworkCollection getArtwork() {
Dispatch art = Dispatch.get(object, "Artwork").toDispatch();
return new ITArtworkCollection(art);
}
}

View File

@@ -1,91 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a collection of track objects.
*
* Note that collection indices are always 1-based.
*
* You can retrieve all the tracks defined for a playlist using
* <code>ITPlaylist.getTracks()</code>.
*
* You can retrieve the currently selected track or tracks using
* <code>iTunes.getSelectedTracks()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITTrackCollection {
protected Dispatch object;
public ITTrackCollection(Dispatch d) {
object = d;
}
/**
* Returns the number of tracks in the collection.
* @return Returns the number of tracks in the collection.
*/
public int getCount() {
return Dispatch.get(object, "Count").getInt();
}
/**
* Returns an ITTrack object corresponding to the given index (1-based).
* @param index Index of the track to retrieve, must be less than or
* equal to <code>ITTrackCollection.getCount()</code>.
* @return Returns an ITTrack object corresponding to the given index.
* Will be set to NULL if no track could be retrieved.
*/
public ITTrack getItem (int index) {
Dispatch item = Dispatch.call(object, "Item", index).toDispatch();
ITTrack track = new ITTrack(item);
if (track.getKind()==ITTrackKind.ITTrackKindFile) {
return new ITFileOrCDTrack(item);
} else if (track.getKind()==ITTrackKind.ITTrackKindCD) {
return new ITFileOrCDTrack(item);
} else if (track.getKind()==ITTrackKind.ITTrackKindURL ) {
return new ITURLTrack(item);
} else {
return track;
}
}
/**
* Returns an ITTrack object corresponding to the given index (1-based).
* @param index Index of the track to retrieve, must be less than or
* equal to <code>ITTrackCollection.getCount()</code>.
* @return Returns an ITTrack object corresponding to the given index.
* Will be set to NULL if no track could be retrieved.
*/
public ITTrack getItemByPlayOrder(int index) {
Dispatch item = Dispatch.call(object, "ItemByPlayOrder", index).toDispatch();
return new ITTrack(item);
}
/**
* Returns an ITTrack object withthe specified name.
* @param name The name of the track to retrieve.
* @return Returns an ITTrack object corresponding to the given index.
* Will be set to NULL if no track could be retrieved.
*/
public ITTrack ItemByName (String name) {
Dispatch item = Dispatch.call(object, "ItemByName", name).toDispatch();
return new ITTrack(item);
}
/**
* Returns an ITTrack object with the specified persistent ID. See the
* documentation on ITObject for more information on persistent IDs.
* @param highID The high 32 bits of the 64-bit persistent ID.
* @param lowID The low 32 bits of the 64-bit persistent ID.
* @return Returns an ITTrack object with the specified persistent ID.
* Will be set to NULL if no track could be retrieved.
*/
public ITTrack getItemByPersistentID (int highID, int lowID) {
Dispatch item = Dispatch.call(object, "ItemByPersistentID", highID, lowID).toDispatch();
return new ITTrack(item);
}
}

View File

@@ -1,15 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the track kind.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITTrackKind {
ITTrackKindUnknown,
ITTrackKindFile,
ITTrackKindCD,
ITTrackKindURL,
ITTrackKindDevice,
ITTrackKindSharedLibrary;
}

View File

@@ -1,175 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a URL track.
*
* A URL track references a network audio stream.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITURLTrack extends ITTrack {
public ITURLTrack (Dispatch d) {
super(d);
}
/**
* Returns the URL of the stream represented by this track.
* @return The URL of the stream represented by this track.
*/
public String getURL () {
return Dispatch.get(object, "URL").getString();
}
/**
* Set the URL of the stream represented by this track.
* @param url The URL of the stream represented by this track.
*/
public void setURL (String url) {
Dispatch.call(object, "URL", url);
}
/**
* Returns true if this track is a podcast track. If a podcast track is an
* <code>IITURLTrack</code>, the podcast episode has not been downloaded.
* @return Returns true if this track is a podcast track.
*/
public boolean isPodcast () {
return Dispatch.get(object, "Podcast").getBoolean();
}
/**
* Returns the category for the track.
* @return Returns the category for the track.
*/
public String getCategory () {
return Dispatch.get(object, "Category").getString();
}
/**
* Sets the category for the track.
* @param category Sets the category for the track.
*/
public void setCategory (String category) {
Dispatch.call(object, "Category", category);
}
/**
* Returns the description for the track.
* @return Returns the description for the track.
*/
public String getDescription () {
return Dispatch.get(object, "Description").getString();
}
/**
* Sets the description for the track.
* @param description The new description for the track.
*/
public void setDescription (String description) {
Dispatch.call(object, "Description", description);
}
/**
* Returns the long description for the track.
* @return Returns the description for the track.
*/
public String getLongDescription () {
return Dispatch.get(object, "LongDescription").getString();
}
/**
* Sets the long description for the track.
* @param longDescription The new long description for the track.
*/
public void setLongDescription (String longDescription) {
Dispatch.call(object, "LongDescription", longDescription);
}
/**
* Returns the user or computed rating of the album that this track belongs
* to (0 to 100). If the album rating has never been set, or has been set to
* 0, it will be computed based on the ratings of tracks in the album.
* @return Returns the album rating of the album that this track belongs to (0 to 100).
*/
public long getAlbumRating () {
return Dispatch.get(object, "AlbumRating").getLong();
}
/**
* Set the album rating of the album that this track belongs to (0 to 100).
* If the album rating is set to 0, it will be computed based on the ratings
* of tracks in the album.
* @param albumRating The new album rating of the album that this track
* belongs to (0 to 100). If rating is outside this range, it will be
* pinned.
*/
public void setAlbumRating (long albumRating) {
Dispatch.call(object, "AlbumRating", albumRating);
}
/**
* Returns the album rating kind. If the album rating has never been set, or
* has been set to 0, the kind is ITRatingKindComputed. Otherwise, the kind
* is ITRatingKindUser.
* @return Returns the album rating kind.
*/
public ITRatingKind getAlbumRatingKind () {
return ITRatingKind.values()[Dispatch.get(object, "AlbumRatingKind").getInt()];
}
/**
* Returns the track rating kind. If the track rating has never been set, or
* has been set to 0, the kind is ITRatingKindComputed. Otherwise, the kind
* is ITRatingKindUser.
* @return Returns the track rating kind.
*/
public ITRatingKind getRatingKind () {
return ITRatingKind.values()[Dispatch.get(object, "RatingKind").getInt()];
}
/**
* Returns a collection of playlists that contain the song that this track
* represents.
*
* This is the same collection of playlists that are shown in the "Show in
* Playlist" contextual menu for a track, plus the specific playlist that
* contains this track.
*
* A track represents a song in a single playlist, use
* <code>ITTrack.getPlaylist()</code> to get the specific playlist that
* contains this track.
* @return Collection of ITPlaylist objects.
*/
public ITPlaylistCollection getPlaylists () {
Dispatch playlists = Dispatch.get(object, "Playlists").toDispatch();
return new ITPlaylistCollection(playlists);
}
/**
* Update the podcast feed for this track. This is equivalent to the user
* choosing Update Podcast from the contextual menu for the podcast feed
* that contains this track.
*/
public void updatePodcastFeed () {
Dispatch.call(object, "UpdatePodcastFeed");
}
/**
* Start downloading the podcast episode that corresponds to this track.
* This is equivalent to the user clicking the Get button next to this
* track.
*/
public void downloadPodcastEpisode () {
Dispatch.call(object, "DownloadPodcastEpisode");
}
/**
* Reveals the track in the main browser window.
*/
public void reveal() {
Dispatch.call(object, "Reveal");
}
}

View File

@@ -1,60 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a user-defined playlist.
*
* A user playlist includes both smart and manual user-defined playlists.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITUserPlaylist extends ITPlaylist {
public ITUserPlaylist(Dispatch d) {
super(d);
}
/**
* Add a file or files inside a folder to the playlist.
* You cannot use this method to add a file that requires conversion to be
* added (e.g. a CD track), use <code>iTunes.convertFile()</code> or
* <code>iTunes.convertFile2()</code> instead. If you add a folder that
* contains files that require conversion, they will be skipped.
* @param filePath The full path to the file or folder to add.
* @return Returns an ITOperationStatus object corresponding to the
* asynchronous operation. If an error occurs, or no files were added, this
* will be set to <code>NULL</code>.
*/
public ITOperationStatus addFile (String filePath) {
Dispatch status = Dispatch.call(object, "AddFile", filePath).toDispatch();
return new ITOperationStatus(status);
}
/**
* Add a streaming audio URL to the playlist.
* @param url The URL to add. The length of the URL can be 255 characters or
* less.
* @return Returns an ITURLTrack object corresponding to the new track.
*/
public ITURLTrack addURL (String url) {
Dispatch URLTrack = Dispatch.call(object, "AddURL", url).toDispatch();
return new ITURLTrack(URLTrack);
}
/**
* Add an existing track to the playlist.
* You cannot use this method to add a CD track (ITTrackKindCD) to another
* playlist, use <code>iTunes.convertTrack()</code> or
* <code>iTunes.convertTrack2()</code> instead.
* You cannot add a shared library track (ITTrackKindSharedLibrary) to
* another playlist.
* @param track The track to add.
* @return Returns an IITTrack object corresponding to the new track.
*/
public ITTrack addTrack (ITTrack track) {
Dispatch trackToAdd = track.fetchDispatch();
Dispatch addedTrack = Dispatch.call(object, "AddTrack", trackToAdd).toDispatch();
return new ITTrack(addedTrack);
}
}

View File

@@ -1,13 +0,0 @@
package com.dt.iTunesController;
/**
* Specifies the Video kind.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public enum ITVideoKind {
ITVideoKindNone,
ITVideoKindMovie,
ITVideoKindMusicVideo,
ITVideoKindTVShow;
}

View File

@@ -1,32 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents an iTunes window.
*/
public class ITWindow {
protected Dispatch object;
public ITWindow(Dispatch d) {
object = d;
}
/**
* Returns the JACOB Dispatch object for this object.
* @return Returns the JACOB Dispatch object for this object.
*/
public Dispatch fetchDispatch() {
return object;
}
/**
* Returns the name of the object.
* @return Returns the name of the object.
*/
public String getName() {
return Dispatch.get(object, "Name").getString();
}
}

View File

@@ -1,55 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
/**
* Represents a collection of window objects.
*
* Note that collection indices are always 1-based.
*
* You can retrieve all the windows using
* <code>iTunes.getWindows()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class ITWindowCollection {
protected Dispatch object;
public ITWindowCollection(Dispatch d) {
object = d;
}
// TODO: iTunes.getWindows()
/**
* Returns the number of playlists in the collection.
* @return Returns the number of playlists in the collection.
*/
public int getCount() {
return Dispatch.get(object, "Count").getInt();
}
/**
* Returns an ITWindow object corresponding to the given index (1-based).
* @param index Index of the playlist to retrieve, must be less than or
* equal to <code>ITWindowCollection.getCount()</code>.
* @return Returns an ITWindow object corresponding to the given index.
* Will be set to NULL if no playlist could be retrieved.
*/
public ITWindow getItem (int index) {
Dispatch item = Dispatch.call(object, "Item", index).toDispatch();
return new ITWindow(item);
}
/**
* Returns an ITWindow object with the specified name.
* @param name The name of the window to retrieve.
* @return Returns an ITWindow object corresponding to the given index.
* Will be set to NULL if no ITWindow could be retrieved.
*/
public ITWindow ItemByName (String name) {
Dispatch item = Dispatch.call(object, "ItemByName", name).toDispatch();
return new ITWindow(item);
}
}

View File

@@ -1,488 +0,0 @@
package com.dt.iTunesController;
import com.jacob.activeX.*;
import com.jacob.com.Dispatch;
import com.jacob.com.DispatchEvents;
import com.jacob.com.Variant;
/**
* Defines the top-level iTunes application object.
*
* This interface defines the top-level iTunes application object. All other
* iTunes interfaces are accessed through this object.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class iTunes {
ActiveXComponent iTunes;
iTunesEvents iTunesEvents;
DispatchEvents dispatchEvents;
/**
* Initiate iTunes Controller.
*/
public iTunes() {
iTunes = new ActiveXComponent("iTunes.Application");
}
/**
* Add an event handler to the iTunes controller.
* @param itef The class that will handle the iTunes events.
*/
public void addEventHandler(iTunesEventsInterface itef) {
iTunesEvents = new iTunesEvents(itef);
dispatchEvents = new DispatchEvents(iTunes, iTunesEvents);
System.out.println("New event handler added.");
}
/**
* Reposition to the beginning of the current track or go to the previous
* track if already at start of current track.
*/
public void backTrack() {
iTunes.invoke("BackTrack");
}
/**
* Skip forward in a playing track.
*/
public void fastForward() {
iTunes.invoke("FastForward");
}
/**
* Advance to the next track in the current playlist.
*/
public void nextTrack() {
iTunes.invoke("NextTrack");
}
/**
* Pause playback.
*/
public void pause() {
iTunes.invoke("Pause");
}
/**
* Play the currently targeted track.
*/
public void play() {
Variant s = iTunes.invoke("ASDSDPlay");
}
/**
* Play the specified file path, adding it to the library if not already
* present.
*/
public void playFile(String filePath) {
iTunes.invoke("PlayFile", filePath);
}
/**
* Toggle the playing/paused state of the current track.
*/
public void playPause() {
iTunes.invoke("PlayPause");
}
/**
* Return to the previous track in the current playlist.
*/
public void previousTrack() {
iTunes.invoke("PreviousTrack");
}
/**
* Disable fast forward/rewind and resume playback, if playing.
*/
public void resume() {
iTunes.invoke("Resume");
}
/**
* Skip backwards in a playing track.
*/
public void rewind() {
iTunes.invoke("Rewind");
}
/**
* Stop playback.
*/
public void stop() {
iTunes.invoke("Stop");
}
/**
* Retrieves the current state of the player buttons in the window
* containing the currently targeted track. If there is no currently
* targeted track, returns the current state of the player buttons
* in the main browser window.
*/
public void getPlayerButtonsState(boolean previousEnabled,
String playPause, boolean nextEnabled) {
}
/**
* Returns true if this version of the iTunes type library is compatible
* with the specified version.
* @param majorVersion Major version of iTunes interface.
* @param minorVersion Minor version of iTunes interface.
* @return Returns true if this version is compatible with the indicated
* interface version.
*/
public boolean getCheckVersion (int majorVersion, int minorVersion) {
return iTunes.invoke("CheckVersion", majorVersion, minorVersion).getBoolean();
}
/**
* Returns an IITObject corresponding to the specified IDs.
* The object may be a source, playlist, or track.
* @param sourceID The ID that identifies the source. Valid for a source,
* playlist, or track.
* @param playlistID The ID that identifies the playlist. Valid for a
* playlist or track. Must be zero for a source.
* @param trackID The ID that identifies the track within the playlist.
* Valid for a track. Must be zero for a source or playlist.
* @param databaseID The ID that identifies the track, independent of its
* playlist. Valid for a track. Must be zero for a source or playlist.
* @return Returns an IITObject object corresponding to the specified IDs.
* Will be set to NULL if no object could be retrieved.
*/
public ITObject getITObjectByID(int sourceID, int playlistID, int trackID, int databaseID) {
Dispatch object = Dispatch.call(iTunes, "GetITObjectByID", sourceID, playlistID, trackID, databaseID).toDispatch();
return new ITObject(object);
}
/**
* Creates a new playlist in the main library.
* @param playlistName The name of the new playlist (may be empty).
* @return Returns an ITPlaylist object corresponding to the new playlist.
*/
public ITPlaylist createPlaylist(String playlistName) {
Dispatch cplaylist = Dispatch.call(iTunes, "CreatePlaylist", playlistName).toDispatch();
ITPlaylist playlist = new ITPlaylist(cplaylist);
ITPlaylistKind playlistKind = playlist.getKind();
if (playlistKind == ITPlaylistKind.ITPlaylistKindCD)
return new ITAudioCDPlaylist(cplaylist);
else if (playlist.getKind() == ITPlaylistKind.ITPlaylistKindLibrary)
return new ITLibraryPlaylist(cplaylist);
else if (playlist.getKind() == ITPlaylistKind.ITPlaylistKindUser)
return new ITUserPlaylist(cplaylist);
else
return playlist;
}
/**
* Open the specified iTunes Store or streaming audio URL.
* @param url The URL to open. The length of the URL cannot exceed 512
* characters. iTunes Store URLs start with itms:// or itmss://. Streaming
* audio URLs start with http://.
*/
public void openURL (String url) {
iTunes.invoke("OpenURL", url);
}
/**
* Go to the iTunes Store home page.
*/
public void gotoMusicStoreHomePage() {
iTunes.invoke("GoToMusicStoreHomePage");
}
/**
* Update the contents of the iPod.
*/
public void updateIPod() {
iTunes.invoke("UpdateIPod");
}
/**
* Exits the iTunes application.
*/
public void quit() {
iTunes.invoke("Quit");
}
/**
* Creates a new EQ preset.
* The EQ preset will be created "flat", i.e. the preamp and all band levels
* will be set to 0.
* EQ preset names cannot start with leading spaces. If you specify a name
* that starts with leading spaces they will be stripped out.
* If <code>eqPresetName</code> is empty, the EQ preset will be created with
* a default name.
* @param eqPresetName The name of the new EQ Preset (may be empty)
* @return Returns an ITEQPreset object corresponding to the new EQ Preset.
*/
public ITEQPreset createEQPreset(String eqPresetName) {
Dispatch eqPreset = Dispatch.call(iTunes, "CreateEQPreset", eqPresetName).toDispatch();
return new ITEQPreset(eqPreset);
}
/**
* Creates a new playlist in an existing source.
* You may not be able to create a playlist in every source. For example,
* you cannot create a playlist in an audio CD source, or in an iPod source
* if it is in auto update mode.
* If <code>playlistName</code> is empty, the playlist will be created with
* a default name.
* @param playlistName The name of the new playlist (may be empty).
* @param source The source that will contain the new playlist.
* @return Returns an ITPlaylist object corresponding to the new playlist.
*/
public ITPlaylist createPlaylistInSource(String playlistName, ITSource source) {
Dispatch cplaylist = Dispatch.call(iTunes, "CreatePlaylistInSource", playlistName, source.fetchDispatch()).toDispatch();
ITPlaylist playlist = new ITPlaylist(cplaylist);
ITPlaylistKind playlistKind = playlist.getKind();
if (playlistKind == ITPlaylistKind.ITPlaylistKindCD)
return new ITAudioCDPlaylist(cplaylist);
else if (playlist.getKind() == ITPlaylistKind.ITPlaylistKindLibrary)
return new ITLibraryPlaylist(cplaylist);
else if (playlist.getKind() == ITPlaylistKind.ITPlaylistKindUser)
return new ITUserPlaylist(cplaylist);
else
return playlist;
}
/**
* Subscribes to the specified podcast feed URL. Any "unsafe" characters in
* the URL should already be converted into their corresponding escape
* sequences, iTunes will not do this.
* @param url The URL to subscribe to.
*/
public void subscribeToPodcast(String url) {
iTunes.invoke("SubscribeToPodcast", url);
}
/**
* Updates all podcast feeds. This is equivalent to the user pressing the
* Update button when Podcasts is selected in the Source list.
*/
public void updatePodcastFeeds() {
iTunes.invoke("UpdatePodcastFeeds");
}
/**
* Creates a new folder in the main library.
* If <code>folderName</code> is empty, the folder will be created with a
* default name.
* @param folderName The name of the new folder (may be empty).
* @return Returns an ITPlaylist object corresponding to the new folder.
*/
public ITUserPlaylist createFolder(String folderName) {
Dispatch folder = Dispatch.call(iTunes, "CreateFolder", folderName).toDispatch();
return new ITUserPlaylist(folder);
}
/**
* Creates a new folder in an existing source.
* You may not be able to create a folder in every source. For example, you
* cannot create a folder in an audio CD source, or in an iPod source if it
* is in auto update mode.
* If <code>folderName</code> is empty, the folder will be created with a
* default name.
* @param folderName The name of the new folder (may be empty)
* @param iSource The source that will contain the new folder.
* @return Returns an ITPlaylist object corresponding to the new folder.
*/
public ITUserPlaylist createFolderInSource(String folderName, ITSource iSource) {
Dispatch folder = Dispatch.call(iTunes, "CreateFolderInSource", folderName, iSource.fetchDispatch()).toDispatch();
return new ITUserPlaylist(folder);
}
/**
* Returns a collection of music sources (music library, CD, device, etc.).
* @return Collection of ITSource objects.
*/
public ITSourceCollection getSources() {
Dispatch sources = Dispatch.call(iTunes, "Sources").toDispatch();
return new ITSourceCollection(sources);
}
/**
* Sets the sound output volume (0=minimum, 100=maximum).
* @param volume New sound output volume
*/
public void setSoundVolume(int volume) {
iTunes.setProperty("SoundVolume", volume);
}
/**
* Returns the sound output volume (0=minimum, 100=maximum).
* @return Current sound output volume
*/
public int getSoundVolume() {
return iTunes.getPropertyAsInt("SoundVolume");
}
/**
* Sets sound output mute state.
* @param shouldMute If true, sound output will be muted.
*/
public void setMute(boolean shouldMute) {
iTunes.setProperty("Mute", shouldMute);
}
/**
* Returns true if the sound output is muted.
* @return True if sound output is muted.
*/
public boolean getMute() {
return iTunes.getPropertyAsBoolean("Mute");
}
/**
* Returns the current player state.
* @return Returns the current player state.
*/
public ITPlayerState getPlayerState() {
return ITPlayerState.values()[Dispatch.get(iTunes, "PlayerState").getInt()];
}
/**
* Sets the player's position within the currently playing track in
* seconds.
* If playerPos specifies a position before the beginning of the track,
* the position will be set to the beginning. If playerPos specifies a
* position after the end of the track, the position will be set to the
* end.
* @param playerPos The player's position within the currently playing
* track in seconds.
*/
public void setPlayerPosition(int playerPos) {
iTunes.setProperty("playerPosition", playerPos);
}
/**
* Returns the player's position within the currently playing track in
* seconds.
* @return The player's position within the currently playing track in
* seconds.
*/
public int getPlayerPosition() {
return iTunes.getPropertyAsInt("playerPosition");
}
/**
* Returns the source that represents the main library.
* You can also find the main library source by iterating over
* <code>iTunes.getSources()</code> and looking for an <code>ITSource</code>
* of kind <code>ITSourceKindLibrary</code>.
* @return Returns the source that represents the main library.
*/
public ITSource getLibrarySource() {
Dispatch lsource = iTunes.getProperty("LibrarySource").toDispatch();
return new ITSource(lsource);
}
/**
* Returns the main library playlist in the main library source.
* @return An IITLibraryPlaylist object corresponding to the main library
* playlist.
*/
public ITLibraryPlaylist getLibraryPlaylist() {
Dispatch lplaylist = iTunes.getProperty("LibraryPlaylist").toDispatch();
return new ITLibraryPlaylist(lplaylist);
}
/**
* Returns the currently targetd track.
* @return An ITTrack object corresponding to the currently targeted track.
* Will be set to NULL if there is no currently targeted track.
*/
public ITTrack getCurrentTrack() {
Dispatch item = iTunes.getProperty("CurrentTrack").toDispatch();
ITTrack track = new ITTrack(item);
if (track.getKind()==ITTrackKind.ITTrackKindFile) {
return new ITFileOrCDTrack(item);
} else if (track.getKind()==ITTrackKind.ITTrackKindCD) {
return new ITFileOrCDTrack(item);
} else if (track.getKind()==ITTrackKind.ITTrackKindURL ) {
return new ITURLTrack(item);
} else {
return track;
}
}
/**
* Returns the playlist containing the currently targeted track.
* @return An ITPlaylist object corresponding to the playlist containing the
* currently targeted track.
* Will be set to NULL if there is no currently targeted playlist.
*/
public ITPlaylist getCurrentPlaylist() {
Dispatch cplaylist = iTunes.getProperty("CurrentPlaylist").toDispatch();
ITPlaylist playlist = new ITPlaylist(cplaylist);
ITPlaylistKind playlistKind = playlist.getKind();
if (playlistKind == ITPlaylistKind.ITPlaylistKindCD)
return new ITAudioCDPlaylist(cplaylist);
else if (playlist.getKind() == ITPlaylistKind.ITPlaylistKindLibrary)
return new ITLibraryPlaylist(cplaylist);
else if (playlist.getKind() == ITPlaylistKind.ITPlaylistKindUser)
return new ITUserPlaylist(cplaylist);
else
return playlist;
}
/**
* Returns a collection containing the currently selected track or tracks.
* The frontmost visible window in iTunes must be a browser or playlist
* window. If there is no frontmost visible window (e.g. iTunes is minimized
* to the system tray), the main browser window is used.
* @return Collection of ITrack objects.
* Will be set to NULL if there is no current selection.
*/
public ITTrackCollection getSelectedTracks() {
Dispatch stracks = iTunes.getProperty("SelectedTracks").toDispatch();
return new ITTrackCollection(stracks);
}
/**
* Returns the version of the iTunes application.
* @return
*/
public String getVersion() {
return iTunes.getPropertyAsString("Version");
}
/**
* Returns the high 32 bits of the persistent ID of the specified IITObject.
* See the documentation on IITObject for more information on persistent
* IDs.
*
* The object may be a source, playlist, or track.
* @param iObject The object to fetch the High Persistent ID.
* @return The high 32 bits of the 64-bit persistent ID.
*/
public long getITObjectPersistentIDHigh (ITObject iObject) {
Dispatch object = iObject.fetchDispatch();
return Dispatch.call(object, "GetObjectPersistentIDHigh", object).getLong();
}
/**
* Returns the low 32 bits of the persistent ID of the specified IITObject.
* See the documentation on IITObject for more information on persistent
* IDs.
*
* The object may be a source, playlist, or track.
* @param iObject The object to fetch the Low Persistent ID.
* @return The low 32 bits of the 64-bit persistent ID.
*/
public long getITObjectPersistentIDLow (ITObject iObject) {
Dispatch object = iObject.fetchDispatch();
return Dispatch.call(object, "GetObjectPersistentIDLow", object).getLong();
}
public ITObjectPersistentID getObjectPersistentIDs(ITObject iObject){
return new ITObjectPersistentID(getITObjectPersistentIDHigh(iObject),getITObjectPersistentIDLow(iObject));
}
public ITBrowserWindow getBrowserWindow(){
Dispatch window = iTunes.getProperty("BrowserWindow").toDispatch();
return new ITBrowserWindow(window);
}
}

View File

@@ -1,62 +0,0 @@
package com.dt.iTunesController;
import com.jacob.com.Dispatch;
import com.jacob.com.Variant;
/**
* This class is used to forward all iTunes COM Events to a class that
* implements <code>iTunesEventsInterface</code>. To receive events, create
* a class that implements the interface, and then use
* <code>iTunes.addEventHandler()</code>.
*
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public class iTunesEvents {
private iTunesEventsInterface eventHandler;
public iTunesEvents (iTunesEventsInterface itef) {
eventHandler = itef;
}
public void OnDatabaseChangedEvent(Variant[] args) {
// Not currently implemented
}
public void OnPlayerPlayEvent(Variant[] args) {
ITTrack itt = new ITTrack((Dispatch)args[0].getDispatch());
eventHandler.onPlayerPlayEvent(itt);
}
public void OnPlayerStopEvent(Variant[] args) {
ITTrack itt = new ITTrack((Dispatch)args[0].getDispatch());
eventHandler.onPlayerStopEvent(itt);
}
public void OnPlayerPlayingTrackChangedEvent(Variant[] args) {
ITTrack itt = new ITTrack((Dispatch)args[0].getDispatch());
eventHandler.onPlayerPlayingTrackChangedEvent(itt);
}
public void OnCOMCallsDisabledEvent(Variant[] args) {
ITCOMDisabledReason reason = ITCOMDisabledReason.values()[args[0].getInt()];
eventHandler.onCOMCallsDisabledEvent(reason);
}
public void OnCOMCallsEnabledEvent(Variant[] args) {
eventHandler.onCOMCallsEnabledEvent();
}
public void OnQuittingEvent(Variant[] args) {
eventHandler.onQuittingEvent();
}
public void OnAboutToPromptUserToQuitEvent(Variant[] args) {
eventHandler.onAboutToPromptUserToQuitEvent();
}
public void OnSoundVolumeChangedEvent(Variant[] args) {
eventHandler.onSoundVolumeChangedEvent(args[0].getInt());
}
}

View File

@@ -1,115 +0,0 @@
package com.dt.iTunesController;
/**
* Interface for receiving iTunes events.
* @author <a href="mailto:steve@dot-totally.co.uk">Steve Eyre</a>
* @version 0.2
*/
public interface iTunesEventsInterface {
/**
* <strong>Not currently implemented</strong>.
*
* The ITEventDatabaseChanged event is fired when the iTunes database is
* changed.
*
* Each parameter is a two-dimensional array of integers. The first
* dimension is the number of objects. The second dimension is always 4 and
* specifies each of the 4 ITObject IDs, where index 0 is the source ID,
* index 1 is the playlist ID, index 2 is the track ID, and index 3 is the
* track database ID. For more information on object IDs, see
* <code>ITObject</code>.
*
* Note that you can use <code>iTunes.getITObjectByID()</code> to retrieve
* changed ITObject, but not for deleted objects (since they no longer
* exist).
*
* @param deletedObjectIDs
* @param changedObjectIDs
*/
public void onDatabaseChangedEvent(int[][] deletedObjectIDs, int[][] changedObjectIDs);
/**
* The ITEventPlayerPlay event is fired when a track begins playing.
* @param iTrack An ITTrack object corresponding to the track that has
* started playing.
*/
public void onPlayerPlayEvent (ITTrack iTrack);
/**
* The ITEventPlayerStop event is fired when a track stops playing.
* @param iTrack An ITTrack object corresponding to the track that has
* stopped playing.
*/
public void onPlayerStopEvent (ITTrack iTrack);
/**
* The ITEventPlayerPlayingTrackChanged event is fired when information
* about the currently playing track has changed.
* This event is fired when the user changes information about the currently
* playing track (e.g. the name of the track).
* This event is also fired when iTunes plays the next joined CD track in a
* CD playlist, since joined CD tracks are treated as a single track.
* @param iTrack An ITTrack object corresponding to the track that is now
* playing.
*/
public void onPlayerPlayingTrackChangedEvent(ITTrack iTrack);
/**
* The ITEventCOMCallsDisabled event is fired when calls to the iTunes COM
* interface will be deferred.
* Typically, iTunes will defer COM calls when any modal dialog is being
* displayed. When the user dismisses the last modal dialog, COM calls will
* be enabled again, and any deferred COM calls will be executed. You can
* use this event to avoid making a COM call which will be deferred.
* @param reason The reason the COM interface is being disabled. This is
* typically <code>ITCOMDisabledReasonDialog</code>.
*/
public void onCOMCallsDisabledEvent(ITCOMDisabledReason reason);
/**
* The ITEventCOMCallsEnabled event is fired when calls to the iTunes COM
* interface will no longer be deferred.
* Typically, iTunes will defer COM calls when any modal dialog is being
* displayed. When the user dismisses the last modal dialog, COM calls will
* be enabled again, and any deferred COM calls will be executed.
*/
public void onCOMCallsEnabledEvent();
/**
* The ITEventQuitting event is fired when iTunes is about to quit.
* If the user attempts to quit iTunes while a client still has outstanding
* iTunes COM objects instantiated, iTunes will display a warning dialog.
* The user can still choose to quit iTunes anyway, in which case this event
* will be fired. After this event is fired, any existing iTunes COM objects
* will no longer be valid.
* This event is only used to notify clients that iTunes is quitting,
* clients cannot prevent this from happening.
*/
public void onQuittingEvent();
/**
* The ITEventAboutToPromptUserToQuit event is fired when iTunes is about
* prompt the user to quit.
* This event gives clients the opportunity to prevent the warning dialog
* prompt from occurring.
* If the user attempts to quit iTunes while a client still has outstanding
* iTunes COM objects instantiated, iTunes will display a warning dialog.
* This event is fired just before the warning dialog is shown. iTunes will
* then wait up to 5 seconds for clients to release any outstanding iTunes
* COM objects. If all objects are released during this time, the warning
* dialog will not be shown and iTunes will quit immediately.
* Otherwise, the warning dialog will be shown. If the user chooses to quit
* iTunes anyway, the ITEventQuitting event is fired. See
* <code>iTunesEventsInterface.onQuittingEvent()</code> for more details.
*/
public void onAboutToPromptUserToQuitEvent();
/**
* The ITEventSoundVolumeChanged event is fired when the sound output volume
* has changed.
* @param newVolume The new sound output volume (0 = minimum, 100 = maximum).
*/
public void onSoundVolumeChangedEvent(int newVolume);
}

View File

@@ -1,479 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.activeX;
import com.jacob.com.Dispatch;
import com.jacob.com.JacobObject;
import com.jacob.com.Variant;
/**
* This class provides a higher level, more object like, wrapper for top of the
* Dispatch object. The Dispatch class's method essentially directly map to
* Microsoft C API including the first parameter that is almost always the
* target of the message. ActiveXComponent assumes the target of every message
* is the MS COM object behind the ActiveXComponent. This removes the need to
* pass the Dispatch object into every method.
* <p>
* It is really up to the developer as to whether they want to use the Dispatch
* interface or the ActiveXComponent interface.
* <p>
* This class simulates com.ms.activeX.ActiveXComponent only in the sense that
* it is used for creating Dispatch objects
*/
public class ActiveXComponent extends Dispatch {
/**
* Normally used to create a new connection to a microsoft application. The
* passed in parameter is the name of the program as registered in the
* registry. It can also be the object name.
* <p>
* This constructor causes a new Windows object of the requested type to be
* created. The windows CoCreate() function gets called to create the
* underlying windows object.
*
* <pre>
* new ActiveXComponent(&quot;ScriptControl&quot;);
* </pre>
*
* @param programId
*/
public ActiveXComponent(String programId) {
super(programId);
}
/**
* Creates an active X component that is built on top of the COM pointers
* held in the passed in dispatch. This widens the Dispatch object to pick
* up the ActiveXComponent API
*
* @param dispatchToBeWrapped
*/
public ActiveXComponent(Dispatch dispatchToBeWrapped) {
super(dispatchToBeWrapped);
}
/**
* only used by the factories
*
*/
private ActiveXComponent() {
super();
}
/**
* Probably was a cover for something else in the past. Should be
* deprecated.
*
* @return Now it actually returns this exact same object.
*/
public Dispatch getObject() {
return this;
}
/**
* Most code should use the standard ActiveXComponent(String) contructor and
* not this factory method. This method exists for applications that need
* special behavior. <B>Experimental in release 1.9.2.</B>
* <p>
* Factory that returns a Dispatch object wrapped around the result of a
* CoCreate() call. This differs from the standard constructor in that it
* throws no exceptions and returns null on failure.
* <p>
* This will fail for any prog id with a ":" in it.
*
* @param pRequestedProgramId
* @return Dispatch pointer to the COM object or null if couldn't create
*/
public static ActiveXComponent createNewInstance(String pRequestedProgramId) {
ActiveXComponent mCreatedDispatch = null;
try {
mCreatedDispatch = new ActiveXComponent();
mCreatedDispatch.coCreateInstance(pRequestedProgramId);
} catch (Exception e) {
mCreatedDispatch = null;
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("Unable to co-create instance of "
+ pRequestedProgramId);
}
}
return mCreatedDispatch;
}
/**
* Most code should use the standard ActiveXComponent(String) constructor
* and not this factory method. This method exists for applications that
* need special behavior. <B>Experimental in release 1.9.2.</B>
* <p>
* Factory that returns a Dispatch wrapped around the result of a
* getActiveObject() call. This differs from the standard constructor in
* that it throws no exceptions and returns null on failure.
* <p>
* This will fail for any prog id with a ":" in it
*
* @param pRequestedProgramId
* @return Dispatch pointer to a COM object or null if wasn't already
* running
*/
public static ActiveXComponent connectToActiveInstance(
String pRequestedProgramId) {
ActiveXComponent mCreatedDispatch = null;
try {
mCreatedDispatch = new ActiveXComponent();
mCreatedDispatch.getActiveInstance(pRequestedProgramId);
} catch (Exception e) {
mCreatedDispatch = null;
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("Unable to attach to running instance of "
+ pRequestedProgramId);
}
}
return mCreatedDispatch;
}
/**
* @see com.jacob.com.Dispatch#finalize()
*/
@Override
protected void finalize() {
super.finalize();
}
/*
* ============================================================
*
* start of instance based calls to the COM layer
* ===========================================================
*/
/**
* retrieves a property and returns it as a Variant
*
* @param propertyName
* @return variant value of property
*/
public Variant getProperty(String propertyName) {
return Dispatch.get(this, propertyName);
}
/**
* retrieves a property and returns it as an ActiveX component
*
* @param propertyName
* @return Dispatch representing the object under the property name
*/
public ActiveXComponent getPropertyAsComponent(String propertyName) {
return new ActiveXComponent(Dispatch.get(this, propertyName)
.toDispatch());
}
/**
* retrieves a property and returns it as a Boolean
*
* @param propertyName
* property we are looking up
* @return boolean value of property
*/
public boolean getPropertyAsBoolean(String propertyName) {
return Dispatch.get(this, propertyName).getBoolean();
}
/**
* retrieves a property and returns it as a byte
*
* @param propertyName
* property we are looking up
* @return byte value of property
*/
public byte getPropertyAsByte(String propertyName) {
return Dispatch.get(this, propertyName).getByte();
}
/**
* retrieves a property and returns it as a String
*
* @param propertyName
* @return String value of property
*/
public String getPropertyAsString(String propertyName) {
return Dispatch.get(this, propertyName).getString();
}
/**
* retrieves a property and returns it as a int
*
* @param propertyName
* @return the property value as an int
*/
public int getPropertyAsInt(String propertyName) {
return Dispatch.get(this, propertyName).getInt();
}
/**
* sets a property on this object
*
* @param propertyName
* property name
* @param arg
* variant value to be set
*/
public void setProperty(String propertyName, Variant arg) {
Dispatch.put(this, propertyName, arg);
}
/**
* sets a property on this object
*
* @param propertyName
* property name
* @param arg
* variant value to be set
*/
public void setProperty(String propertyName, Dispatch arg) {
Dispatch.put(this, propertyName, arg);
}
/**
* sets a property to be the value of the string
*
* @param propertyName
* @param propertyValue
*/
public void setProperty(String propertyName, String propertyValue) {
this.setProperty(propertyName, new Variant(propertyValue));
}
/**
* sets a property as a boolean value
*
* @param propertyName
* @param propValue
* the boolean value we want the prop set to
*/
public void setProperty(String propertyName, boolean propValue) {
this.setProperty(propertyName, new Variant(propValue));
}
/**
* sets a property as a boolean value
*
* @param propertyName
* @param propValue
* the boolean value we want the prop set to
*/
public void setProperty(String propertyName, byte propValue) {
this.setProperty(propertyName, new Variant(propValue));
}
/**
* sets the property as an int value
*
* @param propertyName
* @param propValue
* the int value we want the prop to be set to.
*/
public void setProperty(String propertyName, int propValue) {
this.setProperty(propertyName, new Variant(propValue));
}
/*-------------------------------------------------------
* Listener logging helpers
*-------------------------------------------------------
*/
/**
* This boolean determines if callback events should be logged
*/
public static boolean shouldLogEvents = false;
/**
* used by the doc and application listeners to get intelligent logging
*
* @param description
* event description
* @param args
* args passed in (variants)
*
*/
public void logCallbackEvent(String description, Variant[] args) {
String argString = "";
if (args != null && ActiveXComponent.shouldLogEvents) {
if (args.length > 0) {
argString += " args: ";
}
for (int i = 0; i < args.length; i++) {
short argType = args[i].getvt();
argString += ",[" + i + "]";
// break out the byref bits if they are on this
if ((argType & Variant.VariantByref) == Variant.VariantByref) {
// show the type and the fact that its byref
argString += "("
+ (args[i].getvt() & ~Variant.VariantByref) + "/"
+ Variant.VariantByref + ")";
} else {
// show the type
argString += "(" + argType + ")";
}
argString += "=";
if (argType == Variant.VariantDispatch) {
Dispatch foo = (args[i].getDispatch());
argString += foo;
} else if ((argType & Variant.VariantBoolean) == Variant.VariantBoolean) {
// do the boolean thing
if ((argType & Variant.VariantByref) == Variant.VariantByref) {
// boolean by ref
argString += args[i].getBooleanRef();
} else {
// boolean by value
argString += args[i].getBoolean();
}
} else if ((argType & Variant.VariantString) == Variant.VariantString) {
// do the string thing
if ((argType & Variant.VariantByref) == Variant.VariantByref) {
// string by ref
argString += args[i].getStringRef();
} else {
// string by value
argString += args[i].getString();
}
} else {
argString += args[i].toString();
}
}
System.out.println(description + argString);
}
}
/*
* ==============================================================
*
* covers for dispatch call methods
* =============================================================
*/
/**
* makes a dispatch call for the passed in action and no parameter
*
* @param callAction
* @return ActiveXComponent representing the results of the call
*/
public ActiveXComponent invokeGetComponent(String callAction) {
return new ActiveXComponent(invoke(callAction).toDispatch());
}
/**
* makes a dispatch call for the passed in action and single parameter
*
* @param callAction
* @param parameters
* @return ActiveXComponent representing the results of the call
*/
public ActiveXComponent invokeGetComponent(String callAction,
Variant... parameters) {
return new ActiveXComponent(invoke(callAction, parameters).toDispatch());
}
/**
* invokes a single parameter call on this dispatch that returns no value
*
* @param actionCommand
* @param parameter
* @return a Variant but that may be null for some calls
*/
public Variant invoke(String actionCommand, String parameter) {
return Dispatch.call(this, actionCommand, parameter);
}
/**
* makes a dispatch call to the passed in action with a single boolean
* parameter
*
* @param actionCommand
* @param parameter
* @return Variant result
*/
public Variant invoke(String actionCommand, boolean parameter) {
return Dispatch.call(this, actionCommand, new Variant(parameter));
}
/**
* makes a dispatch call to the passed in action with a single int parameter
*
* @param actionCommand
* @param parameter
* @return Variant result of the invoke (Dispatch.call)
*/
public Variant invoke(String actionCommand, int parameter) {
return Dispatch.call(this, actionCommand, new Variant(parameter));
}
/**
* makes a dispatch call to the passed in action with a string and integer
* parameter (this was put in for some application)
*
* @param actionCommand
* @param parameter1
* @param parameter2
* @return Variant result
*/
public Variant invoke(String actionCommand, String parameter1,
int parameter2) {
return Dispatch.call(this, actionCommand, parameter1, new Variant(
parameter2));
}
/**
* makes a dispatch call to the passed in action with two integer parameters
* (this was put in for some application)
*
* @param actionCommand
* @param parameter1
* @param parameter2
* @return a Variant but that may be null for some calls
*/
public Variant invoke(String actionCommand, int parameter1, int parameter2) {
return Dispatch.call(this, actionCommand, new Variant(parameter1),
new Variant(parameter2));
}
/**
* makes a dispatch call for the passed in action and no parameter
*
* @param callAction
* @return a Variant but that may be null for some calls
*/
public Variant invoke(String callAction) {
return Dispatch.call(this, callAction);
}
/**
* This is really a cover for call(String,Variant[]) that should be
* eliminated call with a variable number of args mainly used for quit.
*
* @param name
* @param args
* @return Variant returned by the invoke (Dispatch.callN)
*/
public Variant invoke(String name, Variant... args) {
return Dispatch.callN(this, name, args);
}
}

View File

@@ -1,106 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.activeX;
import com.jacob.com.Dispatch;
import com.jacob.com.DispatchEvents;
import com.jacob.com.InvocationProxy;
/**
* RELEASE 1.12 EXPERIMENTAL.
* <p>
* Use this exactly like the DispatchEvents class. This class plugs in an
* ActiveXInvocationProxy instead of an InvocationProxy. It is the
* ActiveXInvocationProxy that implements the reflection calls and invoke the
* found java event callbacks. See ActiveXInvocationProxy for details.
*
*
*/
public class ActiveXDispatchEvents extends DispatchEvents {
/**
* This is the most commonly used constructor.
* <p>
* Creates the event callback linkage between the the MS program represented
* by the Dispatch object and the Java object that will receive the
* callback.
*
* @param sourceOfEvent
* Dispatch object who's MS app will generate callbacks
* @param eventSink
* Java object that wants to receive the events
*/
public ActiveXDispatchEvents(Dispatch sourceOfEvent, Object eventSink) {
super(sourceOfEvent, eventSink, null);
}
/**
* None of the samples use this constructor.
* <p>
* Creates the event callback linkage between the the MS program represented
* by the Dispatch object and the Java object that will receive the
* callback.
*
* @param sourceOfEvent
* Dispatch object who's MS app will generate callbacks
* @param eventSink
* Java object that wants to receive the events
* @param progId
* ???
*/
public ActiveXDispatchEvents(Dispatch sourceOfEvent, Object eventSink,
String progId) {
super(sourceOfEvent, eventSink, progId, null);
}
/**
* Creates the event callback linkage between the the MS program represented
* by the Dispatch object and the Java object that will receive the
* callback.
*
* <pre>
* &gt;ActiveXDispatchEvents de =
* new ActiveXDispatchEvents(someDispatch,someEventHAndler,
* &quot;Excel.Application&quot;,
* &quot;C:\\Program Files\\Microsoft Office\\OFFICE11\\EXCEL.EXE&quot;);
*
* @param sourceOfEvent Dispatch object who's MS app will generate callbacks
* @param eventSink Java object that wants to receive the events
* @param progId , mandatory if the typelib is specified
* @param typeLib The location of the typelib to use
*
*/
public ActiveXDispatchEvents(Dispatch sourceOfEvent, Object eventSink,
String progId, String typeLib) {
super(sourceOfEvent, eventSink, progId, typeLib);
}
/*
* (non-Javadoc)
*
* @see com.jacob.com.DispatchEvents#getInvocationProxy(java.lang.Object)
*/
protected InvocationProxy getInvocationProxy(Object pTargetObject) {
InvocationProxy newProxy = new ActiveXInvocationProxy();
newProxy.setTarget(pTargetObject);
return newProxy;
}
}

View File

@@ -1,183 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.activeX;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import com.jacob.com.InvocationProxy;
import com.jacob.com.NotImplementedException;
import com.jacob.com.Variant;
/**
* RELEASE 1.12 EXPERIMENTAL.
* <p>
* This class that lets event handlers receive events with all java objects as
* parameters. The standard Jacob event methods all accept an array of Variant
* objects. When using this class, you can set up your event methods as regular
* java methods with the correct number of parameters of the correct java type.
* This does NOT work for any event that wishes to accept a call back and modify
* the calling parameters to tell windows what to do. An example is when an
* event lets the receiver cancel the action by setting a boolean flag to false.
* The java objects cannot be modified and their values will not be passed back
* into the originating Variants even if they could be modified.
* <p>
* This class acts as a proxy between the windows event callback mechanism and
* the Java classes that are looking for events. It assumes that all of the Java
* classes that are looking for events implement methods with the same names as
* the windows events and that the implemented methods native java objects of
* the type and order that match the windows documentation. The methods can
* return void or a Variant that will be returned to the calling layer. All
* Event methods that will be recognized by InvocationProxyAllEvents have the
* signature
*
* <code> void eventMethodName(Object,Object...)</code> or
* <code> Object eventMethodName(Object,Object...)</code>
*/
public class ActiveXInvocationProxy extends InvocationProxy {
/*
* (non-Javadoc)
*
* @see com.jacob.com.InvocationProxy#invoke(java.lang.String,
* com.jacob.com.Variant[])
*/
@SuppressWarnings("unchecked")
public Variant invoke(String methodName, Variant targetParameters[]) {
Variant mVariantToBeReturned = null;
if (mTargetObject == null) {
// structured programming guidlines say this return should not be up
// here
return null;
}
Class targetClass = mTargetObject.getClass();
if (methodName == null) {
throw new IllegalArgumentException(
"InvocationProxy: missing method name");
}
if (targetParameters == null) {
throw new IllegalArgumentException(
"InvocationProxy: missing Variant parameters");
}
try {
Method targetMethod;
Object parametersAsJavaObjects[] = getParametersAsJavaObjects(targetParameters);
Class parametersAsJavaClasses[] = getParametersAsJavaClasses(parametersAsJavaObjects);
targetMethod = targetClass.getMethod(methodName,
parametersAsJavaClasses);
if (targetMethod != null) {
// protected classes can't be invoked against even if they
// let you grab the method. you could do
// targetMethod.setAccessible(true);
// but that should be stopped by the security manager
Object mReturnedByInvocation = null;
mReturnedByInvocation = targetMethod.invoke(mTargetObject,
parametersAsJavaObjects);
if (mReturnedByInvocation == null) {
mVariantToBeReturned = null;
} else if (!(mReturnedByInvocation instanceof Variant)) {
mVariantToBeReturned = new Variant(mReturnedByInvocation);
} else {
mVariantToBeReturned = (Variant) mReturnedByInvocation;
}
}
} catch (SecurityException e) {
// what causes this exception?
e.printStackTrace();
} catch (NoSuchMethodException e) {
// this happens whenever the listener doesn't implement all the
// methods
} catch (IllegalArgumentException e) {
// we can throw these inside the catch block so need to re-throw it
Exception oneWeShouldToss = new IllegalArgumentException(
"Unable to map parameters for method " + methodName + ": "
+ e.toString());
oneWeShouldToss.printStackTrace();
} catch (IllegalAccessException e) {
// can't access the method on the target instance for some reason
e.printStackTrace();
} catch (InvocationTargetException e) {
// invocation of target method failed
e.printStackTrace();
}
return mVariantToBeReturned;
}
/**
* creates a method signature compatible array of classes from an array of
* parameters
*
* @param parametersAsJavaObjects
* @return
*/
@SuppressWarnings("unchecked")
private Class[] getParametersAsJavaClasses(Object[] parametersAsJavaObjects) {
if (parametersAsJavaObjects == null) {
throw new IllegalArgumentException(
"This only works with an array of parameters");
}
int numParameters = parametersAsJavaObjects.length;
Class parametersAsJavaClasses[] = new Class[numParameters];
for (int parameterIndex = 0; parameterIndex < numParameters; parameterIndex++) {
Object oneParameterObject = parametersAsJavaObjects[parameterIndex];
if (oneParameterObject == null) {
parametersAsJavaClasses[parameterIndex] = null;
} else {
Class oneParameterClass = oneParameterObject.getClass();
parametersAsJavaClasses[parameterIndex] = oneParameterClass;
}
}
return parametersAsJavaClasses;
}
/**
* converts an array of Variants to their associated Java types
*
* @param targetParameters
* @return
*/
private Object[] getParametersAsJavaObjects(Variant[] targetParameters) {
if (targetParameters == null) {
throw new IllegalArgumentException(
"This only works with an array of parameters");
}
int numParameters = targetParameters.length;
Object parametersAsJavaObjects[] = new Object[numParameters];
for (int parameterIndex = 0; parameterIndex < numParameters; parameterIndex++) {
Variant oneParameterObject = targetParameters[parameterIndex];
if (oneParameterObject == null) {
parametersAsJavaObjects[parameterIndex] = null;
} else {
try {
parametersAsJavaObjects[parameterIndex] = oneParameterObject
.toJavaObject();
} catch (NotImplementedException nie) {
throw new IllegalArgumentException(
"Can't convert parameter " + parameterIndex
+ " type " + oneParameterObject.getvt()
+ " to java object: " + nie.getMessage());
}
}
}
return parametersAsJavaObjects;
}
}

View File

@@ -1,141 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* Standard exception thrown by com jni code when there is a problem
*/
public abstract class ComException extends JacobException {
/**
* COM code initializes this filed with an appropriate return code that was
* returned by the underlying com code
*/
protected int hr;
/**
* No documentation is available at this time. Someone should document this
* field
*/
protected int m_helpContext;
/**
* No documentation is available at this time. Someone should document this
* field
*/
protected String m_helpFile;
/**
* No documentation is available at this time. Someone should document this
* field
*/
protected String m_source;
/**
* constructor
*
*/
public ComException() {
super();
}
/**
* constructor with error code?
*
* @param newHr ??
*/
public ComException(int newHr) {
super();
this.hr = newHr;
}
/**
* @param newHr
* @param description
*/
public ComException(int newHr, String description) {
super(description);
this.hr = newHr;
}
/**
* @param newHr
* @param source
* @param helpFile
* @param helpContext
*/
public ComException(int newHr, String source, String helpFile,
int helpContext) {
super();
this.hr = newHr;
m_source = source;
m_helpFile = helpFile;
m_helpContext = helpContext;
}
/**
* @param newHr
* @param description
* @param source
* @param helpFile
* @param helpContext
*/
public ComException(int newHr, String description, String source,
String helpFile, int helpContext) {
super(description);
this.hr = newHr;
m_source = source;
m_helpFile = helpFile;
m_helpContext = helpContext;
}
/**
* @param description
*/
public ComException(String description) {
super(description);
}
/**
* @return int representation of the help context
*/
// Methods
public int getHelpContext() {
return m_helpContext;
}
/**
* @return String ??? help file
*/
public String getHelpFile() {
return m_helpFile;
}
/**
* @return int hr result ??
*/
public int getHResult() {
return hr;
}
/**
* @return String source ??
*/
public String getSource() {
return m_source;
}
}

View File

@@ -1,88 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* COM Fail Exception class raised when there is a problem
*/
public class ComFailException extends ComException {
/**
* eclipse generated to get rid of a wanring
*/
private static final long serialVersionUID = -266047261992987700L;
/**
* Constructor
*
* @param hrNew
*/
public ComFailException(int hrNew) {
super(hrNew);
}
/**
* Constructor
*
* @param hrNew
* @param message
*/
public ComFailException(int hrNew, String message) {
super(hrNew, message);
}
/**
* @param hrNew
* @param source
* @param helpFile
* @param helpContext
*/
public ComFailException(int hrNew, String source, String helpFile,
int helpContext) {
super(hrNew, source, helpFile, helpContext);
}
/**
* Constructor
*
* @param hrNew
* @param description
* @param source
* @param helpFile
* @param helpContext
*/
public ComFailException(int hrNew, String description, String source,
String helpFile, int helpContext) {
super(hrNew, description, source, helpFile, helpContext);
}
/**
* No argument Constructor
*/
public ComFailException() {
super();
}
/**
* @param message
*/
public ComFailException(String message) {
super(message);
}
}

View File

@@ -1,169 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* Represents a COM level thread This is an abstract class because all the
* methods are static and no instances are ever created.
*/
public abstract class ComThread {
private static final int MTA = 0x0;
private static final int STA = 0x2;
/**
* Comment for <code>haveSTA</code>
*/
public static boolean haveSTA = false;
/**
* Comment for <code>mainSTA</code>
*/
public static MainSTA mainSTA = null;
/**
* Initialize the current java thread to be part of the Multi-threaded COM
* Apartment
*/
public static synchronized void InitMTA() {
InitMTA(false);
}
/**
* Initialize the current java thread to be an STA
*/
public static synchronized void InitSTA() {
InitSTA(false);
}
/**
* Initialize the current java thread to be part of the Multi-threaded COM
* Apartment, if createMainSTA is true, create a separate MainSTA thread
* that will house all Apartment Threaded components
*
* @param createMainSTA
*/
public static synchronized void InitMTA(boolean createMainSTA) {
Init(createMainSTA, MTA);
}
/**
* Initialize the current java thread to be an STA COM Apartment, if
* createMainSTA is true, create a separate MainSTA thread that will house
* all Apartment Threaded components
*
* @param createMainSTA
*/
public static synchronized void InitSTA(boolean createMainSTA) {
Init(createMainSTA, STA);
}
/**
*
*/
public static synchronized void startMainSTA() {
mainSTA = new MainSTA();
haveSTA = true;
}
/**
*
*/
public static synchronized void quitMainSTA() {
if (mainSTA != null)
mainSTA.quit();
}
/**
* Initialize the current java thread to be part of the MTA/STA COM
* Apartment
*
* @param createMainSTA
* @param mode
*/
public static synchronized void Init(boolean createMainSTA, int mode) {
if (createMainSTA && !haveSTA) {
// if the current thread is going to be in the MTA and there
// is no STA thread yet, then create a main STA thread
// to avoid COM creating its own
startMainSTA();
}
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ComThread: before Init: " + mode);
}
doCoInitialize(mode);
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ComThread: after Init: " + mode);
}
ROT.addThread();
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ComThread: after ROT.addThread: " + mode);
}
}
/**
* Call CoUninitialize to release this java thread from COM
*/
public static synchronized void Release() {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ComThread: before clearObjects");
}
ROT.clearObjects();
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ComThread: before UnInit");
}
doCoUninitialize();
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ComThread: after UnInit");
}
}
/**
* @deprecated the java model leave the responsibility of clearing up
* objects to the Garbage Collector. Our programming model
* should not require that the user specifically remove object
* from the thread.
*
* This will remove an object from the ROT
* @param o
*/
@Deprecated
public static synchronized void RemoveObject(JacobObject o) {
ROT.removeObject(o);
}
/**
* @param threadModel
*/
public static native void doCoInitialize(int threadModel);
/**
*
*/
public static native void doCoUninitialize();
/**
* load the Jacob DLL. We do this in case COMThread is called before any
* other reference to one of the JacboObject subclasses is made.
*/
static {
LibraryLoader.loadJacobLibrary();
}
}

View File

@@ -1,91 +0,0 @@
package com.jacob.com;
/**
* Most COM bridges use java.lang.Long as their Java data type for COM Currency
* data. This is because COM currency is a 64 bit number where the last 4 digits
* represent the milli-cents. We wanted to support 64 bit Long values for x64
* platforms so that meant we wanted to map Java.LONG to COM.LONG even though it
* only works for 64 bit platforms. The end result was we needed a new
* representation for Money so we have this.
* <p>
* In the future, this should convert to and from BigDecimal or Double
*/
public class Currency {
Long embeddedValue = null;
/**
* constructor that takes a long already in COM representation
*
* @param newValue
*/
public Currency(long newValue) {
embeddedValue = new Long(newValue);
}
/**
* constructor that takes a String already in COM representation
*
* @param newValue
*/
public Currency(String newValue) {
embeddedValue = new Long(newValue);
}
/**
*
* @return the currency as a primitive long
*/
public long longValue() {
return embeddedValue.longValue();
}
/**
* getter to the inner storage so that cmpareTo can work
*
* @return the embedded long value
*/
protected Long getLongValue() {
return embeddedValue;
}
/**
* compares the values of two currencies
*
* @param anotherCurrency
* @return the usual compareTo results
*/
public int compareTo(Currency anotherCurrency) {
return embeddedValue.compareTo(anotherCurrency.getLongValue());
}
/**
* standard comparison
*
* @param o
* must be Currency or Long
* @return the usual compareTo results
*/
public int compareTo(Object o) {
if (o instanceof Currency) {
return compareTo((Currency) o);
} else if (o instanceof Long) {
return embeddedValue.compareTo((Long) o);
} else
throw new IllegalArgumentException(
"Can only compare to Long and Currency not "
+ o.getClass().getName());
}
/**
* {@inheritDoc}
*/
public boolean equals(Object o) {
if (o == null) {
return false;
} else if (compareTo(o) == 0) {
return true;
} else {
return false;
}
}
}

View File

@@ -1,105 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
import java.util.Calendar;
import java.util.Date;
/**
* java / windows date conversion utilities
*
* @author joe
*
*/
public class DateUtilities {
/**
* converts a windows time to a Java Date Object
*
* @param comTime
* @return Date object representing the windows time as specified in comTime
*/
static public Date convertWindowsTimeToDate(double comTime) {
return new Date(convertWindowsTimeToMilliseconds(comTime));
}
/**
* Convert a COM time from functions Date(), Time(), Now() to a Java time
* (milliseconds). Visual Basic time values are based to 30.12.1899, Java
* time values are based to 1.1.1970 (= 0 milliseconds). The difference is
* added to the Visual Basic value to get the corresponding Java value. The
* Visual Basic double value reads: <day count delta since 30.12.1899>.<1
* day percentage fraction>, e.g. "38100.6453" means: 38100 days since
* 30.12.1899 plus (24 hours * 0.6453). Example usage:
* <code>Date javaDate = new Date(toMilliseconds (vbDate));</code>.
*
* @param comTime
* COM time.
* @return Java time.
*/
static public long convertWindowsTimeToMilliseconds(double comTime) {
long result = 0;
// code from jacobgen:
comTime = comTime - 25569D;
Calendar cal = Calendar.getInstance();
result = Math.round(86400000L * comTime)
- cal.get(Calendar.ZONE_OFFSET);
cal.setTime(new Date(result));
result -= cal.get(Calendar.DST_OFFSET);
return result;
}// convertWindowsTimeToMilliseconds()
/**
* converts a java date to a windows time object (is this timezone safe?)
*
* @param javaDate
* the java date to be converted to windows time
* @return the double representing the date in a form windows understands
*/
static public double convertDateToWindowsTime(Date javaDate) {
if (javaDate == null) {
throw new IllegalArgumentException(
"cannot convert null to windows time");
}
return convertMillisecondsToWindowsTime(javaDate.getTime());
}
/**
* Convert a Java time to a COM time.
*
* @param milliseconds
* Java time.
* @return COM time.
*/
static public double convertMillisecondsToWindowsTime(long milliseconds) {
double result = 0.0;
// code from jacobgen:
Calendar cal = Calendar.getInstance();
cal.setTimeInMillis(milliseconds);
milliseconds += (cal.get(Calendar.ZONE_OFFSET) + cal
.get(Calendar.DST_OFFSET)); // add GMT offset
result = (milliseconds / 86400000D) + 25569D;
return result;
}// convertMillisecondsToWindowsTime()
}

View File

@@ -1,872 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project. All rights reserved. Originator: Dan Adler
* (http://danadler.com). Get more information about JACOB at
* http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or modify it under the terms of the
* GNU Lesser General Public License as published by the Free Software Foundation; either version
* 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without
* even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License along with this library;
* if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA
*/
package com.jacob.com;
/**
* Object represents MS level dispatch object. Each instance of this points at
* some data structure on the MS windows side.
*
*
* <p>
* You're going to live here a lot
*/
public class Dispatch extends JacobObject {
/**
* Used to set the locale in a call. The user locale is another option
*/
public static final int LOCALE_SYSTEM_DEFAULT = 2048;
/** used by callN() and callSubN() */
public static final int Method = 1;
/** used by callN() and callSubN() */
public static final int Get = 2;
/** used by put() */
public static final int Put = 4;
/** not used, probably intended for putRef() */
public static final int PutRef = 8;
/**
* One of legal values for GetDispId. Not used in this layer and probably
* not needed.
*/
public static final int fdexNameCaseSensitive = 1;
/**
* This is public because Dispatch.cpp knows its name and accesses it
* directly to get the dispatch id. You really can't rename it or make it
* private
*/
public int m_pDispatch;
/** program Id passed in by ActiveX components in their constructor */
private String programId = null;
private static int NOT_ATTACHED = 0;
/**
* Dummy empty array used one doesn't have to be created on every invocation
*/
private final static Object[] NO_OBJECT_ARGS = new Object[0];
/**
* Dummy empty array used one doesn't have to be created on every invocation
*/
private final static Variant[] NO_VARIANT_ARGS = new Variant[0];
/**
* Dummy empty array used one doesn't have to be created on every invocation
*/
private final static int[] NO_INT_ARGS = new int[0];
/**
* zero argument constructor that sets the dispatch pointer to 0 This is the
* only way to create a Dispatch without a value in the pointer field.
*/
public Dispatch() {
m_pDispatch = NOT_ATTACHED;
}
/**
* This constructor calls createInstance with progid. This is the
* constructor used by the ActiveXComponent or by programs that don't like
* the activeX interface but wish to create new connections to windows
* programs.
* <p>
* This constructor always creates a new windows/program object because it
* is based on the CoCreate() windows function.
* <p>
*
* @param requestedProgramId
* @throws IllegalArgumentException
* if null is passed in as the program id
* <p>
*/
public Dispatch(String requestedProgramId) {
programId = requestedProgramId;
if (programId != null && !"".equals(programId)) {
createInstanceNative(requestedProgramId);
} else {
throw new IllegalArgumentException(
"Dispatch(String) does not accept null or an empty string as a parameter");
}
}
/**
* native call createInstance only used by the constructor with the same
* parm type. This probably should be private. It is the wrapper for the
* Windows CoCreate() call
* <P>
* This ends up calling CoCreate down in the JNI layer
* <p>
* The behavior is different if a ":" character exists in the progId. In
* that case CoGetObject and CreateInstance (someone needs to describe this
* better)
*
* @param progid
*/
private native void createInstanceNative(String progid);
/**
* native call getActiveInstance only used by the constructor with the same
* parm type. This probably should be private. It is the wrapper for the
* Windows GetActiveObject() call
* <P>
* This ends up calling GetActiveObject down in the JNI layer
* <p>
* This does not have the special behavior for program ids with ":" in them
* that createInstance has.
*
* @param progid
*/
private native void getActiveInstanceNative(String progid);
/**
* Wrapper around the native method
*
* @param pProgramIdentifier
* name of the program you wish to connect to
*/
protected void getActiveInstance(String pProgramIdentifier) {
if (pProgramIdentifier == null || "".equals(pProgramIdentifier)) {
throw new IllegalArgumentException("program id is required");
}
this.programId = pProgramIdentifier;
getActiveInstanceNative(pProgramIdentifier);
}
/**
* native call coCreateInstance only used by the constructor with the same
* parm type. This probably should be private. It is the wrapper for the
* Windows CoCreate() call
* <P>
* This ends up calling CoCreate down in the JNI layer
* <p>
* This does not have the special behavior for program ids with ":" in them
* that createInstance has.
*
* @param progid
*/
private native void coCreateInstanceNative(String progid);
/**
* Wrapper around the native method
*
* @param pProgramIdentifier
*/
protected void coCreateInstance(String pProgramIdentifier) {
if (pProgramIdentifier == null || "".equals(pProgramIdentifier)) {
throw new IllegalArgumentException("program id is required");
}
this.programId = pProgramIdentifier;
coCreateInstanceNative(pProgramIdentifier);
}
/**
* Return a different interface by IID string.
* <p>
* Once you have a Dispatch object, you can navigate to the other interfaces
* of a COM object by calling QueryInterafce. The argument is an IID string
* in the format: "{9BF24410-B2E0-11D4-A695-00104BFF3241}". You typically
* get this string from the idl file (it's called uuid in there). Any
* interface you try to use must be derived from IDispatch. T The atl
* example uses this.
* <p>
* The Dispatch instance resulting from this query is instanciated in the
* JNI code.
*
* @param iid
* @return Dispatch a disptach that matches ??
*/
public native Dispatch QueryInterface(String iid);
/**
* Constructor that only gets called from JNI QueryInterface calls JNI code
* that looks up the object for the key passed in. The JNI CODE then creates
* a new dispatch object using this constructor
*
* @param pDisp
*/
protected Dispatch(int pDisp) {
m_pDispatch = pDisp;
}
/**
* Constructor to be used by subclass that want to swap themselves in for
* the default Dispatch class. Usually you will have a class like
* WordDocument that is a subclass of Dispatch and it will have a
* constructor public WordDocument(Dispatch). That constructor should just
* call this constructor as super(Dispatch)
*
* @param dispatchToBeDisplaced
*/
public Dispatch(Dispatch dispatchToBeDisplaced) {
// TAKE OVER THE IDispatch POINTER
this.m_pDispatch = dispatchToBeDisplaced.m_pDispatch;
// NULL OUT THE INPUT POINTER
dispatchToBeDisplaced.m_pDispatch = NOT_ATTACHED;
}
/**
* returns the program id if an activeX component created this otherwise it
* returns null. This was added to aid in debugging
*
* @return the program id an activeX component was created against
*/
public String getProgramId() {
return programId;
}
/*
* (non-Javadoc)
*
* @see java.lang.Object#finalize()
*/
@Override
protected void finalize() {
safeRelease();
}
/*
* (non-Javadoc)
*
* @see com.jacob.com.JacobObject#safeRelease()
*/
@Override
public void safeRelease() {
super.safeRelease();
if (isAttached()) {
release();
m_pDispatch = NOT_ATTACHED;
} else {
// looks like a double release
if (isDebugEnabled()) {
debug(this.getClass().getName() + ":" + this.hashCode()
+ " double release");
}
}
}
/**
*
* @return true if there is an underlying windows dispatch object
*/
protected boolean isAttached() {
if (m_pDispatch == NOT_ATTACHED) {
return false;
} else {
return true;
}
}
/**
* @param theOneInQuestion
* dispatch being tested
* @throws IllegalStateException
* if this dispatch isn't hooked up
* @throws IllegalArgumentException
* if null the dispatch under test is null
*/
private static void throwIfUnattachedDispatch(Dispatch theOneInQuestion) {
if (theOneInQuestion == null) {
throw new IllegalArgumentException(
"Can't pass in null Dispatch object");
} else if (theOneInQuestion.isAttached()) {
return;
} else {
throw new IllegalStateException(
"Dispatch not hooked to windows memory");
}
}
/**
* now private so only this object can access was: call this to explicitly
* release the com object before gc
*
*/
private native void release();
/**
* not implemented yet
*
* @param dispatchTarget
* @param name
* @param val
* @throws com.jacob.com.NotImplementedException
*/
public static void put_Casesensitive(Dispatch dispatchTarget, String name,
Object val) {
throw new NotImplementedException("not implemented yet");
}
/*
* ============================================================ start of the
* invokev section
* ===========================================================
*/
// eliminate _Guid arg
/**
* @param dispatchTarget
* @param name
* @param dispID
* @param lcid
* @param wFlags
* @param vArg
* @param uArgErr
*/
public static void invokeSubv(Dispatch dispatchTarget, String name,
int dispID, int lcid, int wFlags, Variant[] vArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
invokev(dispatchTarget, name, dispID, lcid, wFlags, vArg, uArgErr);
}
/**
* @param dispatchTarget
* @param name
* @param wFlags
* @param vArg
* @param uArgErr
*/
public static void invokeSubv(Dispatch dispatchTarget, String name,
int wFlags, Variant[] vArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
invokev(dispatchTarget, name, 0, Dispatch.LOCALE_SYSTEM_DEFAULT,
wFlags, vArg, uArgErr);
}
/**
* @param dispatchTarget
* @param dispID
* @param wFlags
* @param vArg
* @param uArgErr
*/
public static void invokeSubv(Dispatch dispatchTarget, int dispID,
int wFlags, Variant[] vArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
invokev(dispatchTarget, null, dispID, Dispatch.LOCALE_SYSTEM_DEFAULT,
wFlags, vArg, uArgErr);
}
/**
* not implemented yet
*
* @param dispatchTarget
* @param name
* @param values
* @return never returns anything because
* @throws com.jacob.com.NotImplementedException
*/
public static Variant callN_CaseSensitive(Dispatch dispatchTarget,
String name, Object[] values) {
throw new NotImplementedException("not implemented yet");
}
/**
* @param dispatchTarget
* @param name
* @param args
* an array of argument objects
*/
public static void callSubN(Dispatch dispatchTarget, String name,
Object... args) {
throwIfUnattachedDispatch(dispatchTarget);
invokeSubv(dispatchTarget, name, Dispatch.Method | Dispatch.Get,
VariantUtilities.objectsToVariants(args), new int[args.length]);
}
/**
* @param dispatchTarget
* @param dispID
* @param args
* an array of argument objects
*/
public static void callSubN(Dispatch dispatchTarget, int dispID,
Object... args) {
throwIfUnattachedDispatch(dispatchTarget);
invokeSubv(dispatchTarget, dispID, Dispatch.Method | Dispatch.Get,
VariantUtilities.objectsToVariants(args), new int[args.length]);
}
/*
* ============================================================ start of the
* getIdsOfNames section
* ===========================================================
*/
/**
* @param dispatchTarget
* @param name
* @return int id for the passed in name
*/
public static int getIDOfName(Dispatch dispatchTarget, String name) {
int ids[] = getIDsOfNames(dispatchTarget,
Dispatch.LOCALE_SYSTEM_DEFAULT, new String[] { name });
return ids[0];
}
/**
* @param dispatchTarget
* @param lcid
* @param names
* @return int[] in id array for passed in names
*/
// eliminated _Guid argument
public static native int[] getIDsOfNames(Dispatch dispatchTarget, int lcid,
String[] names);
/**
* @param dispatchTarget
* @param names
* @return int[] int id array for passed in names
*/
// eliminated _Guid argument
public static int[] getIDsOfNames(Dispatch dispatchTarget, String[] names) {
return getIDsOfNames(dispatchTarget, Dispatch.LOCALE_SYSTEM_DEFAULT,
names);
}
/*
* ============================================================ start of the
* invokev section
* ===========================================================
*/
/**
* @param dispatchTarget
* @param name
* @param args
* @return Variant returned by call
*/
public static Variant callN(Dispatch dispatchTarget, String name,
Object... args) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, name, Dispatch.Method | Dispatch.Get,
VariantUtilities.objectsToVariants(args), new int[args.length]);
}
/**
* @param dispatchTarget
* @param dispID
* @param args
* @return Variant returned by call
*/
public static Variant callN(Dispatch dispatchTarget, int dispID,
Object... args) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, dispID, Dispatch.Method | Dispatch.Get,
VariantUtilities.objectsToVariants(args), new int[args.length]);
}
/**
* @param dispatchTarget
* @param name
* @param dispID
* @param lcid
* @param wFlags
* @param oArg
* @param uArgErr
* @return Variant returned by invoke
*/
public static Variant invoke(Dispatch dispatchTarget, String name,
int dispID, int lcid, int wFlags, Object[] oArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, name, dispID, lcid, wFlags,
VariantUtilities.objectsToVariants(oArg), uArgErr);
}
/**
* @param dispatchTarget
* @param name
* @param wFlags
* @param oArg
* @param uArgErr
* @return Variant returned by invoke
*/
public static Variant invoke(Dispatch dispatchTarget, String name,
int wFlags, Object[] oArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, name, wFlags, VariantUtilities
.objectsToVariants(oArg), uArgErr);
}
/**
* @param dispatchTarget
* @param dispID
* @param wFlags
* @param oArg
* @param uArgErr
* @return Variant returned by invoke
*/
public static Variant invoke(Dispatch dispatchTarget, int dispID,
int wFlags, Object[] oArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, dispID, wFlags, VariantUtilities
.objectsToVariants(oArg), uArgErr);
}
/*
* ============================================================ start of the
* callN section ===========================================================
*/
/**
* @param dispatchTarget
* @param name
* @return Variant returned by underlying callN
*/
public static Variant call(Dispatch dispatchTarget, String name) {
throwIfUnattachedDispatch(dispatchTarget);
return callN(dispatchTarget, name, NO_VARIANT_ARGS);
}
/**
* @param dispatchTarget
* @param name
* @param attributes
* @return Variant returned by underlying callN
*/
public static Variant call(Dispatch dispatchTarget, String name,
Object... attributes) {
throwIfUnattachedDispatch(dispatchTarget);
return callN(dispatchTarget, name, attributes);
}
/**
* @param dispatchTarget
* @param dispid
* @return Variant returned by underlying callN
*/
public static Variant call(Dispatch dispatchTarget, int dispid) {
throwIfUnattachedDispatch(dispatchTarget);
return callN(dispatchTarget, dispid, NO_VARIANT_ARGS);
}
/**
* @param dispatchTarget
* @param dispid
* @param attributes
* var arg list of attributes that will be passed to the
* underlying function
* @return Variant returned by underlying callN
*/
public static Variant call(Dispatch dispatchTarget, int dispid,
Object... attributes) {
throwIfUnattachedDispatch(dispatchTarget);
return callN(dispatchTarget, dispid, attributes);
}
/*
* ============================================================ start of the
* invoke section
* ===========================================================
*/
/**
* @param dispatchTarget
* @param name
* @param val
*/
public static void put(Dispatch dispatchTarget, String name, Object val) {
throwIfUnattachedDispatch(dispatchTarget);
invoke(dispatchTarget, name, Dispatch.Put, new Object[] { val },
new int[1]);
}
/**
* @param dispatchTarget
* @param dispid
* @param val
*/
public static void put(Dispatch dispatchTarget, int dispid, Object val) {
throwIfUnattachedDispatch(dispatchTarget);
invoke(dispatchTarget, dispid, Dispatch.Put, new Object[] { val },
new int[1]);
}
/*
* ============================================================ start of the
* invokev section
* ===========================================================
*/
// removed _Guid argument
/**
* @param dispatchTarget
* @param name
* @param dispID
* @param lcid
* @param wFlags
* @param vArg
* @param uArgErr
* @return Variant returned by underlying invokev
*/
public static native Variant invokev(Dispatch dispatchTarget, String name,
int dispID, int lcid, int wFlags, Variant[] vArg, int[] uArgErr);
/**
* @param dispatchTarget
* @param name
* @param wFlags
* @param vArg
* @param uArgErr
* @return Variant returned by underlying invokev
*/
public static Variant invokev(Dispatch dispatchTarget, String name,
int wFlags, Variant[] vArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, name, 0, Dispatch.LOCALE_SYSTEM_DEFAULT,
wFlags, vArg, uArgErr);
}
/**
* @param dispatchTarget
* @param name
* @param wFlags
* @param vArg
* @param uArgErr
* @param wFlagsEx
* @return Variant returned by underlying invokev
*/
public static Variant invokev(Dispatch dispatchTarget, String name,
int wFlags, Variant[] vArg, int[] uArgErr, int wFlagsEx) {
throwIfUnattachedDispatch(dispatchTarget);
// do not implement IDispatchEx for now
return invokev(dispatchTarget, name, 0, Dispatch.LOCALE_SYSTEM_DEFAULT,
wFlags, vArg, uArgErr);
}
/**
* @param dispatchTarget
* @param dispID
* @param wFlags
* @param vArg
* @param uArgErr
* @return Variant returned by underlying invokev
*/
public static Variant invokev(Dispatch dispatchTarget, int dispID,
int wFlags, Variant[] vArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, null, dispID,
Dispatch.LOCALE_SYSTEM_DEFAULT, wFlags, vArg, uArgErr);
}
/*
* ============================================================ start of the
* invokeSubv section
* ===========================================================
*/
// removed _Guid argument
/**
* @param dispatchTarget
* @param name
* @param dispid
* @param lcid
* @param wFlags
* @param oArg
* @param uArgErr
*/
public static void invokeSub(Dispatch dispatchTarget, String name,
int dispid, int lcid, int wFlags, Object[] oArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
invokeSubv(dispatchTarget, name, dispid, lcid, wFlags, VariantUtilities
.objectsToVariants(oArg), uArgErr);
}
/*
* ============================================================ start of the
* invokeSub section
* ===========================================================
*/
/**
* @param dispatchTarget
* @param name
* @param wFlags
* @param oArg
* @param uArgErr
*/
public static void invokeSub(Dispatch dispatchTarget, String name,
int wFlags, Object[] oArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
invokeSub(dispatchTarget, name, 0, Dispatch.LOCALE_SYSTEM_DEFAULT,
wFlags, oArg, uArgErr);
}
/**
* @param dispatchTarget
* @param dispid
* @param wFlags
* @param oArg
* @param uArgErr
*/
public static void invokeSub(Dispatch dispatchTarget, int dispid,
int wFlags, Object[] oArg, int[] uArgErr) {
throwIfUnattachedDispatch(dispatchTarget);
invokeSub(dispatchTarget, null, dispid, Dispatch.LOCALE_SYSTEM_DEFAULT,
wFlags, oArg, uArgErr);
}
/*
* ============================================================ start of the
* callSubN section
* ===========================================================
*/
/**
* makes call to native callSubN
*
* @param dispatchTarget
* @param name
*/
public static void callSub(Dispatch dispatchTarget, String name) {
throwIfUnattachedDispatch(dispatchTarget);
callSubN(dispatchTarget, name, NO_OBJECT_ARGS);
}
/**
* makes call to native callSubN
*
* @param dispatchTarget
* @param name
* @param attributes
* var args list of attributes to be passed to underlying
* functions
*/
public static void callSub(Dispatch dispatchTarget, String name,
Object... attributes) {
throwIfUnattachedDispatch(dispatchTarget);
callSubN(dispatchTarget, name, attributes);
}
/**
* makes call to native callSubN
*
* @param dispatchTarget
* @param dispid
*/
public static void callSub(Dispatch dispatchTarget, int dispid) {
throwIfUnattachedDispatch(dispatchTarget);
callSubN(dispatchTarget, dispid, NO_OBJECT_ARGS);
}
/**
* makes call to native callSubN
*
* @param dispatchTarget
* @param dispid
* @param attributes
* var args list of attributes to be passed to underlying
* function
*/
public static void callSub(Dispatch dispatchTarget, int dispid,
Object... attributes) {
throwIfUnattachedDispatch(dispatchTarget);
callSubN(dispatchTarget, dispid, attributes);
}
/*
* ============================================================ start of the
* invokev section
* ===========================================================
*/
/**
* Cover for call to underlying invokev()
*
* @param dispatchTarget
* @param name
* @return Variant returned by the request for retrieval of parameter
*/
public static Variant get(Dispatch dispatchTarget, String name) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, name, Dispatch.Get, NO_VARIANT_ARGS,
NO_INT_ARGS);
}
/**
* Cover for call to underlying invokev()
*
* @param dispatchTarget
* @param dispid
* @return Variant returned by the request for retrieval of parameter
*/
public static Variant get(Dispatch dispatchTarget, int dispid) {
throwIfUnattachedDispatch(dispatchTarget);
return invokev(dispatchTarget, dispid, Dispatch.Get, NO_VARIANT_ARGS,
NO_INT_ARGS);
}
/*
* ============================================================ start of the
* invoke section
* ===========================================================
*/
/**
* cover for underlying call to invoke
*
* @param dispatchTarget
* @param name
* @param val
*/
public static void putRef(Dispatch dispatchTarget, String name, Object val) {
throwIfUnattachedDispatch(dispatchTarget);
invoke(dispatchTarget, name, Dispatch.PutRef, new Object[] { val },
new int[1]);
}
/**
* cover for underlying call to invoke
*
* @param dispatchTarget
* @param dispid
* @param val
*/
public static void putRef(Dispatch dispatchTarget, int dispid, Object val) {
throwIfUnattachedDispatch(dispatchTarget);
invoke(dispatchTarget, dispid, Dispatch.PutRef, new Object[] { val },
new int[1]);
}
/**
* not implemented yet
*
* @param dispatchTarget
* @param name
* @return Variant never returned
* @throws com.jacob.com.NotImplementedException
*/
public static Variant get_CaseSensitive(Dispatch dispatchTarget, String name) {
throw new NotImplementedException("not implemented yet");
}
/**
* Cover for native method
*
* @param disp
* @param dispid
* @param lcid
* @return 0 if the dispatch is still active and 1 if it has exited
*/
public static native int hasExited(Dispatch disp, int dispid, int lcid);
/**
* The method is used to poll until it returns 1, indicating that the COM
* server in gone.
* <p>
* Sourceforge feature request 2927058
*
* @param dispatchTarget
* @return 0 if the dispatch is still active and 1 if it has exited
*/
public static int hasExited(Dispatch dispatchTarget) {
throwIfUnattachedDispatch(dispatchTarget);
return hasExited(dispatchTarget, 0, LOCALE_SYSTEM_DEFAULT);
}
}

View File

@@ -1,219 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* This class creates the scaffolding for event callbacks. Every instance of tis
* acts as a wrapper around some java object that wants callbacks from the
* microsoft side. It represents the connection between Java and COM for
* callbacks.
* <p>
* The callback mechanism will take any event that it receives and try and find
* a java method with the same name that accepts the Variant... as a parameter.
* It will then wrap the call back data in the Variant array and call the java
* method of the object that this DispatchEvents object was initialized with.
* <p>
* Instances of this class are created with "sink object" that will receive the
* event messages. The sink object is wrapped in an Invocation handler that
* actually receives the messages and then forwards them on to the "sink
* object". The constructors recognize when an instance of InvocationProxy is
* passed in and do not create a new InvocationProxy as a wrapper. They instead
* use the passed in InvocationProxy.
*
*/
public class DispatchEvents extends JacobObject {
/**
* pointer to an MS data struct. The COM layer knows the name of this
* variable and puts the windows memory pointer here.
*/
int m_pConnPtProxy = 0;
/**
* the wrapper for the event sink. This object is the one that will be sent
* a message when an event occurs in the MS layer. Normally, the
* InvocationProxy will forward the messages to a wrapped object that it
* contains.
*/
InvocationProxy mInvocationProxy = null;
/**
* This is the most commonly used constructor.
* <p>
* Creates the event callback linkage between the the MS program represented
* by the Dispatch object and the Java object that will receive the
* callback.
* <p>
* Can be used on any object that implements IProvideClassInfo.
*
* @param sourceOfEvent
* Dispatch object who's MS app will generate callbacks
* @param eventSink
* Java object that wants to receive the events
*/
public DispatchEvents(Dispatch sourceOfEvent, Object eventSink) {
this(sourceOfEvent, eventSink, null);
}
/**
* None of the samples use this constructor.
* <p>
* Creates the event callback linkage between the the MS program represented
* by the Dispatch object and the Java object that will receive the
* callback.
* <p>
* Used when the program doesn't implement IProvideClassInfo. It provides a
* way to find the TypeLib in the registry based on the programId. The
* TypeLib is looked up in the registry on the path
* HKEY_LOCAL_MACHINE/SOFTWARE/Classes/CLSID/(CLID drived from
* progid)/ProgID/Typelib
*
* @param sourceOfEvent
* Dispatch object who's MS app will generate callbacks
* @param eventSink
* Java object that wants to receive the events
* @param progId
* program id in the registry that has a TypeLib subkey. The
* progrId is mapped to a CLSID that is they used to look up the
* key to the Typelib
*/
public DispatchEvents(Dispatch sourceOfEvent, Object eventSink,
String progId) {
this(sourceOfEvent, eventSink, progId, null);
}
/**
* Creates the event callback linkage between the the MS program represented
* by the Dispatch object and the Java object that will receive the
* callback.
* <p>
* This method was added because Excel doesn't implement IProvideClassInfo
* and the registry entry for Excel.Application doesn't include a typelib
* key.
*
* <pre>
* DispatchEvents de = new DispatchEvents(someDispatch, someEventHAndler,
* &quot;Excel.Application&quot;,
* &quot;C:\\Program Files\\Microsoft Office\\OFFICE11\\EXCEL.EXE&quot;);
* </pre>
*
* @param sourceOfEvent
* Dispatch object who's MS app will generate callbacks
* @param eventSink
* Java object that wants to receive the events
* @param progId ,
* mandatory if the typelib is specified
* @param typeLib
* The location of the typelib to use
*/
public DispatchEvents(Dispatch sourceOfEvent, Object eventSink,
String progId, String typeLib) {
if (JacobObject.isDebugEnabled()) {
System.out.println("DispatchEvents: Registering " + eventSink
+ "for events ");
}
if (eventSink instanceof InvocationProxy) {
mInvocationProxy = (InvocationProxy) eventSink;
} else {
mInvocationProxy = getInvocationProxy(eventSink);
}
if (mInvocationProxy != null) {
init3(sourceOfEvent, mInvocationProxy, progId, typeLib);
} else {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("Cannot register null event sink for events");
}
throw new IllegalArgumentException(
"Cannot register null event sink for events");
}
}
/**
* Returns an instance of the proxy configured with pTargetObject as its
* target
*
* @param pTargetObject
* @return InvocationProxy an instance of the proxy this DispatchEvents will
* send to the COM layer
*/
protected InvocationProxy getInvocationProxy(Object pTargetObject) {
InvocationProxy newProxy = new InvocationProxyAllVariants();
newProxy.setTarget(pTargetObject);
return newProxy;
}
/**
* hooks up a connection point proxy by progId event methods on the sink
* object will be called by name with a signature of <name>(Variant[] args)
*
* You must specify the location of the typeLib.
*
* @param src
* dispatch that is the source of the messages
* @param sink
* the object that will receive the messages
* @param progId
* optional program id. most folks don't need this either
* @param typeLib
* optional parameter for those programs that don't register
* their type libs (like Excel)
*/
private native void init3(Dispatch src, Object sink, String progId,
String typeLib);
/**
* now private so only this object can asccess was: call this to explicitly
* release the com object before gc
*
*/
private native void release();
/*
* (non-Javadoc)
*
* @see java.lang.Object#finalize()
*/
protected void finalize() {
safeRelease();
}
/*
* (non-Javadoc)
*
* @see com.jacob.com.JacobObject#safeRelease()
*/
public void safeRelease() {
if (mInvocationProxy != null) {
mInvocationProxy.setTarget(null);
}
mInvocationProxy = null;
super.safeRelease();
if (m_pConnPtProxy != 0) {
release();
m_pConnPtProxy = 0;
} else {
// looks like a double release
if (isDebugEnabled()) {
debug("DispatchEvents:" + this.hashCode() + " double release");
}
}
}
}

View File

@@ -1,82 +0,0 @@
/**
*
*/
package com.jacob.com;
/**
* A bunch of DispatchIds that were pulled out of the Dispatch class for version
* 1.14.
*/
public class DispatchIdentifier {
private DispatchIdentifier() {
// This is utility class so there is no constructor.
}
public static final int DISPID_UNKNOWN = -1;
public static final int DISPID_VALUE = 0;
public static final int DISPID_PROPERTYPUT = -3;
public static final int DISPID_NEWENUM = -4;
public static final int DISPID_EVALUATE = -5;
public static final int DISPID_CONSTRUCTOR = -6;
public static final int DISPID_DESTRUCTOR = -7;
public static final int DISPID_COLLECT = -8;
public static final int DISPID_AUTOSIZE = -500;
public static final int DISPID_BACKCOLOR = -501;
public static final int DISPID_BACKSTYLE = -502;
public static final int DISPID_BORDERCOLOR = -503;
public static final int DISPID_BORDERSTYLE = -504;
public static final int DISPID_BORDERWIDTH = -505;
public static final int DISPID_DRAWMODE = -507;
public static final int DISPID_DRAWSTYLE = -508;
public static final int DISPID_DRAWWIDTH = -509;
public static final int DISPID_FILLCOLOR = -510;
public static final int DISPID_FILLSTYLE = -511;
public static final int DISPID_FONT = -512;
public static final int DISPID_FORECOLOR = -513;
public static final int DISPID_ENABLED = -514;
public static final int DISPID_HWND = -515;
public static final int DISPID_TABSTOP = -516;
public static final int DISPID_TEXT = -517;
public static final int DISPID_CAPTION = -518;
public static final int DISPID_BORDERVISIBLE = -519;
public static final int DISPID_APPEARANCE = -520;
public static final int DISPID_MOUSEPOINTER = -521;
public static final int DISPID_MOUSEICON = -522;
public static final int DISPID_PICTURE = -523;
public static final int DISPID_VALID = -524;
public static final int DISPID_READYSTATE = -525;
public static final int DISPID_REFRESH = -550;
public static final int DISPID_DOCLICK = -551;
public static final int DISPID_ABOUTBOX = -552;
public static final int DISPID_CLICK = -600;
public static final int DISPID_DBLCLICK = -601;
public static final int DISPID_KEYDOWN = -602;
public static final int DISPID_KEYPRESS = -603;
public static final int DISPID_KEYUP = -604;
public static final int DISPID_MOUSEDOWN = -605;
public static final int DISPID_MOUSEMOVE = -606;
public static final int DISPID_MOUSEUP = -607;
public static final int DISPID_ERROREVENT = -608;
public static final int DISPID_READYSTATECHANGE = -609;
public static final int DISPID_AMBIENT_BACKCOLOR = -701;
public static final int DISPID_AMBIENT_DISPLAYNAME = -702;
public static final int DISPID_AMBIENT_FONT = -703;
public static final int DISPID_AMBIENT_FORECOLOR = -704;
public static final int DISPID_AMBIENT_LOCALEID = -705;
public static final int DISPID_AMBIENT_MESSAGEREFLECT = -706;
public static final int DISPID_AMBIENT_SCALEUNITS = -707;
public static final int DISPID_AMBIENT_TEXTALIGN = -708;
public static final int DISPID_AMBIENT_USERMODE = -709;
public static final int DISPID_AMBIENT_UIDEAD = -710;
public static final int DISPID_AMBIENT_SHOWGRABHANDLES = -711;
public static final int DISPID_AMBIENT_SHOWHATCHING = -712;
public static final int DISPID_AMBIENT_DISPLAYASDEFAULT = -713;
public static final int DISPID_AMBIENT_SUPPORTSMNEMONICS = -714;
public static final int DISPID_AMBIENT_AUTOCLIP = -715;
public static final int DISPID_AMBIENT_APPEARANCE = -716;
public static final int DISPID_AMBIENT_CODEPAGE = -725;
public static final int DISPID_AMBIENT_PALETTE = -726;
public static final int DISPID_AMBIENT_CHARSET = -727;
public static final int DISPID_AMBIENT_TRANSFERPRIORITY = -728;
}

View File

@@ -1,92 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* If you need to pass a COM Dispatch object between STA threads, you have to
* marshall the interface. This class is used as follows: the STA that creates
* the Dispatch object must construct an instance of this class. Another thread
* can then call toDispatch() on that instance and get a Dispatch pointer which
* has been marshalled. WARNING: You can only call toDispatch() once! If you
* need to call it multiple times (or from multiple threads) you need to
* construct a separate DispatchProxy instance for each such case!
*/
public class DispatchProxy extends JacobObject {
/**
* Comment for <code>m_pStream</code>
*/
public int m_pStream;
/**
* Marshals the passed in dispatch into the stream
*
* @param localDispatch
*/
public DispatchProxy(Dispatch localDispatch) {
MarshalIntoStream(localDispatch);
}
/**
*
* @return Dispatch the dispatch retrieved from the stream
*/
public Dispatch toDispatch() {
return MarshalFromStream();
}
private native void MarshalIntoStream(Dispatch d);
private native Dispatch MarshalFromStream();
/**
* now private so only this object can access was: call this to explicitly
* release the com object before gc
*
*/
private native void release();
/*
* (non-Javadoc)
*
* @see java.lang.Object#finalize()
*/
public void finalize() {
safeRelease();
}
/*
* (non-Javadoc)
*
* @see com.jacob.com.JacobObject#safeRelease()
*/
public void safeRelease() {
super.safeRelease();
if (m_pStream != 0) {
release();
m_pStream = 0;
} else {
// looks like a double release
if (isDebugEnabled()) {
debug(this.getClass().getName() + ":" + this.hashCode()
+ " double release");
}
}
}
}

View File

@@ -1,156 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* An implementation of IEnumVariant based on code submitted by Thomas Hallgren
* (mailto:Thomas.Hallgren@eoncompany.com)
*/
public class EnumVariant extends JacobObject implements
java.util.Enumeration<Variant> {
private int m_pIEnumVARIANT;
private final Variant[] m_recBuf = new Variant[1];
// this only gets called from JNI
//
protected EnumVariant(int pIEnumVARIANT) {
m_pIEnumVARIANT = pIEnumVARIANT;
}
/**
* @param disp
*/
public EnumVariant(Dispatch disp) {
int[] hres = new int[1];
Variant evv = Dispatch.invokev(disp, DispatchIdentifier.DISPID_NEWENUM,
Dispatch.Get, new Variant[0], hres);
if (evv.getvt() != Variant.VariantObject)
//
// The DISPID_NEWENUM did not result in a valid object
//
throw new ComFailException("Can't obtain EnumVARIANT");
EnumVariant tmp = evv.toEnumVariant();
m_pIEnumVARIANT = tmp.m_pIEnumVARIANT;
tmp.m_pIEnumVARIANT = 0;
}
/**
* Implements java.util.Enumeration
*
* @return boolean true if there are more elements in this enumeration
*/
public boolean hasMoreElements() {
{
if (m_recBuf[0] == null) {
if (this.Next(m_recBuf) <= 0)
return false;
}
return true;
}
}
/**
* Implements java.util.Enumeration
*
* @return next element in the enumeration
*/
public Variant nextElement() {
Variant last = m_recBuf[0];
if (last == null) {
if (this.Next(m_recBuf) <= 0)
throw new java.util.NoSuchElementException();
last = m_recBuf[0];
}
m_recBuf[0] = null;
return last;
}
/**
* Get next element in collection or null if at end
*
* @return Variant that is next in the collection
* @deprecated use nextElement() instead
*/
@Deprecated
public Variant Next() {
if (hasMoreElements())
return nextElement();
return null;
}
/**
* This should be private and wrapped to protect JNI layer.
*
* @param receiverArray
* @return Returns the next variant object pointer as an int from windows
* layer
*/
public native int Next(Variant[] receiverArray);
/**
* This should be private and wrapped to protect JNI layer.
*
* @param count
* number to skip
*/
public native void Skip(int count);
/**
* This should be private and wrapped to protect JNI layer
*/
public native void Reset();
/**
* now private so only this object can access was: call this to explicitly
* release the com object before gc
*
*/
private native void release();
/*
* (non-Javadoc)
*
* @see java.lang.Object#finalize()
*/
protected void finalize() {
safeRelease();
}
/*
* (non-Javadoc)
*
* @see com.jacob.com.JacobObject#safeRelease()
*/
public void safeRelease() {
super.safeRelease();
if (m_pIEnumVARIANT != 0) {
this.release();
m_pIEnumVARIANT = 0;
} else {
// looks like a double release
if (isDebugEnabled()) {
debug(this.getClass().getName() + ":" + this.hashCode()
+ " double release");
}
}
}
}

View File

@@ -1,108 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* @version $Id$
* @author joe
*
* DispatchEvents wraps this class around any event handlers before making the
* JNI call that sets up the link with EventProxy. This means that
* EventProxy.cpp just calls invoke(String,Variant[]) against the instance of
* this class. Then this class does reflection against the event listener to
* call the actual event methods. The event methods can return void or return a
* Variant. Any value returned will be passed back to the calling windows module
* by the Jacob JNI layer.
* <p>
*
* The void returning signature is the standard legacy signature. The Variant
* returning signature was added in 1.10 to support event handlers returning
* values.
*
*/
public abstract class InvocationProxy {
/**
* the object we will try and forward to.
*/
protected Object mTargetObject = null;
/**
* dummy constructor for subclasses that don't actually wrap anything and
* just want to override the invoke() method
*/
protected InvocationProxy() {
super();
}
/**
* The method actually invoked by EventProxy.cpp. The method name is
* calculated by the underlying JNI code from the MS windows Callback
* function name. The method is assumed to take an array of Variant objects.
* The method may return a Variant or be a void. Those are the only two
* options that will not blow up.
* <p>
* Subclasses that override this should make sure mTargetObject is not null
* before processing.
*
* @param methodName
* name of method in mTargetObject we will invoke
* @param targetParameters
* Variant[] that is the single parameter to the method
* @return an object that will be returned to the com event caller
*/
public abstract Variant invoke(String methodName,
Variant targetParameters[]);
/**
* used by EventProxy.cpp to create variant objects in the right thread
*
* @return Variant object that will be used by the COM layer
*/
public Variant getVariant() {
return new VariantViaEvent();
}
/**
* Sets the target for this InvocationProxy.
*
* @param pTargetObject
* @throws IllegalArgumentException
* if target is not publicly accessible
*/
public void setTarget(Object pTargetObject) {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("InvocationProxy: setting target "
+ pTargetObject);
}
if (pTargetObject != null) {
// JNI code apparently bypasses this check and could operate against
// protected classes. This seems like a security issue...
// maybe it was because JNI code isn't in a package?
if (!java.lang.reflect.Modifier.isPublic(pTargetObject.getClass()
.getModifiers())) {
throw new IllegalArgumentException(
"InvocationProxy only public classes can receive event notifications");
}
}
mTargetObject = pTargetObject;
}
}

View File

@@ -1,123 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* This class acts as a proxy between the windows event callback mechanism and
* the Java classes that are looking for events. It assumes that all of the Java
* classes that are looking for events implement methods with the same names as
* the windows events and that the implemented methods accept an array of
* variant objects. The methods can return void or a Variant that will be
* returned to the calling layer. All Event methods that will be recognized by
* InvocationProxyAllEvents have the signature
*
* <code> void eventMethodName(Variant[])</code> or
* <code> Variant eventMethodName(Variant[])</code>
*/
public class InvocationProxyAllVariants extends InvocationProxy {
/*
* (non-Javadoc)
*
* @see com.jacob.com.InvocationProxy#invoke(java.lang.String,
* com.jacob.com.Variant[])
*/
@SuppressWarnings("unchecked")
public Variant invoke(String methodName, Variant targetParameters[]) {
Variant mVariantToBeReturned = null;
if (mTargetObject == null) {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("InvocationProxy: received notification ("
+ methodName + ") with no target set");
}
// structured programming guidlines say this return should not be up
// here
return null;
}
Class targetClass = mTargetObject.getClass();
if (methodName == null) {
throw new IllegalArgumentException(
"InvocationProxy: missing method name");
}
if (targetParameters == null) {
throw new IllegalArgumentException(
"InvocationProxy: missing Variant parameters");
}
try {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("InvocationProxy: trying to invoke "
+ methodName + " on " + mTargetObject);
}
Method targetMethod;
targetMethod = targetClass.getMethod(methodName,
new Class[] { Variant[].class });
if (targetMethod != null) {
// protected classes can't be invoked against even if they
// let you grab the method. you could do
// targetMethod.setAccessible(true);
// but that should be stopped by the security manager
Object mReturnedByInvocation = null;
mReturnedByInvocation = targetMethod.invoke(mTargetObject,
new Object[] { targetParameters });
if (mReturnedByInvocation == null) {
mVariantToBeReturned = null;
} else if (!(mReturnedByInvocation instanceof Variant)) {
// could try and convert to Variant here.
throw new IllegalArgumentException(
"InvocationProxy: invokation of target method returned "
+ "non-null non-variant object: "
+ mReturnedByInvocation);
} else {
mVariantToBeReturned = (Variant) mReturnedByInvocation;
}
}
} catch (SecurityException e) {
// what causes this exception?
e.printStackTrace();
} catch (NoSuchMethodException e) {
// this happens whenever the listener doesn't implement all the
// methods
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("InvocationProxy: listener (" + mTargetObject
+ ") doesn't implement " + methodName);
}
} catch (IllegalArgumentException e) {
e.printStackTrace();
// we can throw these inside the catch block so need to re-throw it
throw e;
} catch (IllegalAccessException e) {
// can't access the method on the target instance for some reason
if (JacobObject.isDebugEnabled()) {
JacobObject
.debug("InvocationProxy: probably tried to access public method on non public class"
+ methodName);
}
e.printStackTrace();
} catch (InvocationTargetException e) {
// invocation of target method failed
e.printStackTrace();
}
return mVariantToBeReturned;
}
}

View File

@@ -1,49 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* The parent class of all Jacob exceptions. They all used to be based off of
* RuntimeException or ComException but it was decided to base them all off of
* one owned by this project.
*/
public class JacobException extends RuntimeException {
/**
*
*/
private static final long serialVersionUID = -1637125318746002715L;
/**
* Default constructor. Calls super with a "No Message Provided" string
*/
public JacobException() {
super("No Message Provided");
}
/**
* standard constructor
*
* @param message
*/
public JacobException(String message) {
super(message);
}
}

View File

@@ -1,110 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* The superclass of all Jacob objects. It is used to create a standard API
* framework and to facilitate memory management for Java and COM memory
* elements.
* <p>
* All instances of this class and subclasses are automatically managed by the
* ROT. This means the ROT cannot be a subclass of JacobObject.
* <p>
* All COM object created by JACOB extend this class so that we can
* automatically release them when the thread is detached from COM - if we leave
* it to the finalizer it will call the release from another thread, which may
* result in a segmentation violation.
*/
public class JacobObject {
/**
* Standard constructor that adds this JacobObject to the memory management
* pool.
*/
public JacobObject() {
ROT.addObject(this);
}
/**
* Finalizers call this method. This method should release any COM data
* structures in a way that it can be called multiple times. This can happen
* if someone manually calls this and then a finalizer calls it.
*/
public void safeRelease() {
// currently does nothing - subclasses may do something
if (isDebugEnabled()) {
// this used to do a toString() but that is bad for SafeArray
debug("SafeRelease: " + this.getClass().getName());
}
}
/**
* When things go wrong, it is useful to be able to debug the ROT.
*/
private static final boolean DEBUG =
// true;
"true".equalsIgnoreCase(System.getProperty("com.jacob.debug"));
protected static boolean isDebugEnabled() {
return DEBUG;
}
/**
* Loads JacobVersion.Properties and returns the value of version in it
*
* @deprecated use JacobReleaseInfo.getBuildDate() instead.
* @return String value of version in JacobVersion.Properties or "" if none
*/
@Deprecated
public static String getBuildDate() {
return JacobReleaseInfo.getBuildDate();
}
/**
* Loads JacobVersion.Properties and returns the value of version in it
*
* @deprecated use JacobReleaseInfo.getBuildVersion() instead.
* @return String value of version in JacobVersion.Properties or "" if none
*/
@Deprecated
public static String getBuildVersion() {
return JacobReleaseInfo.getBuildVersion();
}
/**
* Very basic debugging function.
*
* @param istrMessage
*/
protected static void debug(String istrMessage) {
if (isDebugEnabled()) {
System.out.println(Thread.currentThread().getName() + ": "
+ istrMessage);
}
}
/**
* force the jacob DLL to be loaded whenever this class is referenced
*/
static {
LibraryLoader.loadJacobLibrary();
}
}

View File

@@ -1,96 +0,0 @@
package com.jacob.com;
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;
/**
* An interface to the version properties file. This code was removed from
* JacobObject because it doesn't belong there.
*
*/
public class JacobReleaseInfo {
/**
* holds the build version as retrieved from the version properties file
* that exists in the JAR. This can be retrieved by calling the static
* method getBuildVersion()
*
* @see #getBuildVersion()
*/
private static String buildVersion = "";
/**
* holds the build date as retrieved from the version properties file that
* exists in the JAR This can be retrieved by calling the static method
* getBuildDate()
*
* @see #getBuildDate()
*/
private static String buildDate = "";
/** the name of the jacob version properties file */
private static final String PROPERTY_FILE_NAME = "META-INF/JacobVersion.properties";
/**
* Loads version information from PROPERTY_FILE_NAME that was built as part
* of this release.
*
* @throws IllegalStateException
* when it can't find the version properties file
*/
private static void loadVersionProperties() {
Properties versionProps = new Properties();
// can't use system class loader cause won't work in JavaWebStart
InputStream stream = JacobReleaseInfo.class.getClassLoader()
.getResourceAsStream(PROPERTY_FILE_NAME);
// This should never happen. This is an attempt to make something work
// for WebSphere. They may be using some kind of Servlet loader that
// needs an absolute path based search
if (stream == null) {
stream = JacobReleaseInfo.class.getClassLoader()
.getResourceAsStream("/" + PROPERTY_FILE_NAME);
}
// A report came in that WebSphere had trouble finding the file
// so lets trap it. Plus, it's a good idea anyway.
if (stream == null) {
throw new IllegalStateException(
"Can't find "
+ PROPERTY_FILE_NAME
+ " using JacobReleaseInfo.class.getClassLoader().getResourceAsStream()");
} else {
try {
versionProps.load(stream);
stream.close();
buildVersion = (String) versionProps.get("version");
buildDate = (String) versionProps.get("build.date");
} catch (IOException ioe) {
ioe.printStackTrace();
System.err.println("Warning! Couldn't load props " + ioe);
}
}
}
/**
* loads PROPERT_FILE_NAME and returns the value of version in it
*
* @return String value of version in PROPERT_FILE_NAME or "" if none
*/
public static String getBuildDate() {
if (buildDate.equals("")) {
loadVersionProperties();
}
return buildDate;
}
/**
* loads PROPERT_FILE_NAME and returns the value of version in it
*
* @return String value of version in PROPERT_FILE_NAME or "" if none
*/
public static String getBuildVersion() {
if (buildVersion.equals("")) {
loadVersionProperties();
}
return buildVersion;
}
}

View File

@@ -1,230 +0,0 @@
/*
* Copyright (c) 1999-2007 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
import java.util.Enumeration;
import java.util.HashSet;
import java.util.Locale;
import java.util.MissingResourceException;
import java.util.ResourceBundle;
import java.util.Set;
/**
* Utility class to centralize the way in which the jacob JNI library is loaded.
* <p>
*
* This supports defining the path or library name using system properties or a
* custom resource file. If desired, jacob can auto-detect the correct version
* of the DLL for 32 or 64 bit windows, as long as you have named them
* differently.
*
* <ol>
* <li> If system property {@link #JACOB_DLL_PATH} is defined, the file located
* there will be loaded as the jacob dll using System.load(). </li>
*
* <li> If system property {@link #JACOB_DLL_NAME} is defined, the file located
* there will be loaded as the jacob dll. </li>
* <li> If system property {@link #JACOB_DLL_NAME_X86} and
* {@link #JACOB_DLL_NAME_X64} are defined, the file located there will be
* loaded as the jacob dll, depending on the version of Windows. </li>
*
* <li> If {@link #JACOB_DLL_NAME} is defined in the
* {@code com.jacob.com.JacobLibraryLoader} resource file, the specified dll
* will be loaded from the {@code java.library.path}. </li>
* <li> If {@link #JACOB_DLL_NAME_X86} and {@link #JACOB_DLL_NAME_X64} are
* defined in the {@code com.jacob.com.JacobLibraryLoader} resource file, the
* specified dll will be loaded from the {@code java.library.path}, depending
* on the version of Windows. </li>
*
* <li> If none of the above are true, the default is to load the library named
* "jacob-&lt;version&gt;-&lt;arch&gt" (or
* "jacob-&lt;version&gt;-&lt;arch&rt;.dll") from the {@code java.library.path}.
* </li>
* </ol>
*
* The standard behavior for most applications is that {@code LoadLibrary()}
* will be called to load the dll. {@code LoadLibary()} searches directories
* specified in the variable {@code java.library.path}. This is why most test
* cases specify -Djava.library.path in their command line arguments.
* <p>
* JACOB_DLL_PATH submitted sourceforge ticket 1493647 Added 1.11 <br>
* JACOB_DLL_NAME, JACOB_DLL_NAME_32, JACOB_DLL_NAME_64 submitted sourceforge
* ticket 1845039 Added 1.14M7
*
* @author Scott Dickerson (sjd78)
* @author Jason Smith
*/
public final class LibraryLoader {
/**
* Name of system property (currently <tt>jacob.dll.path</tt>) that may
* contain an absolute path to the JNI library.
*/
public static final String JACOB_DLL_PATH = "jacob.dll.path";
/**
* Name of system property (currently <tt>jacob.dll.name</tt>) that may
* contain an alternate name for the JNI library (default is 'jacob').
*/
public static final String JACOB_DLL_NAME = "jacob.dll.name";
/**
* Name of system property (currently <tt>jacob.dll.name</tt>) that may
* contain an alternate name for the JNI library (default is 'jacob'), 32
* bit windows.
*/
public static final String JACOB_DLL_NAME_X86 = "jacob.dll.name.x86";
/**
* Name of system property (currently <tt>jacob.dll.name</tt>) that may
* contain an alternate name for the JNI library (default is 'jacob'), 64
* bit windows.
*/
public static final String JACOB_DLL_NAME_X64 = "jacob.dll.name.x64";
/**
* Appended to "jacob" when building DLL name This string must EXACTLY match
* the string in the build.xml file
*/
public static final String DLL_NAME_MODIFIER_32_BIT = "x86";
/**
* Appended to "jacob" when building DLL name This string must EXACTLY match
* the string in the build.xml file
*/
public static final String DLL_NAME_MODIFIER_64_BIT = "x64";
/**
* Load the jacob dll either from an absolute path or by a library name,
* both of which may be defined in various ways.
*
* @throws UnsatisfiedLinkError
* if the library does not exist.
*/
public static void loadJacobLibrary() {
// In some cases, a library that uses Jacob won't be able to set system
// properties
// prior to Jacob being loaded. The resource bundle provides an
// alternate way to
// override DLL name or path that will be loaded with Jacob regardless
// of other
// initialization order.
ResourceBundle resources = null;
Set<String> keys = new HashSet<String>();
try {
resources = ResourceBundle.getBundle(LibraryLoader.class.getName(),
Locale.getDefault(), LibraryLoader.class.getClassLoader());
for (Enumeration<String> i = resources.getKeys(); i
.hasMoreElements();) {
String key = i.nextElement();
keys.add(key);
}
} catch (MissingResourceException e) {
// Do nothing. Expected.
}
// First, check for a defined PATH. System property overrides resource
// bundle.
String path = System.getProperty(JACOB_DLL_PATH);
if (path == null && resources != null && keys.contains(JACOB_DLL_PATH)) {
path = (String) resources.getObject(JACOB_DLL_PATH);
}
if (path != null) {
JacobObject.debug("Loading library " + path
+ " using System.loadLibrary ");
System.load(path);
} else {
// Path was not defined, so use the OS mechanism for loading
// libraries.
// Check for a defined NAME. System property overrides resource
// bundle.
String name = null;
if (System.getProperty(JACOB_DLL_NAME) != null) {
name = System.getProperty(JACOB_DLL_NAME);
} else if (System.getProperty(JACOB_DLL_NAME_X86) != null
&& shouldLoad32Bit()) {
name = System.getProperty(JACOB_DLL_NAME_X86);
} else if (System.getProperty(JACOB_DLL_NAME_X64) != null
&& !shouldLoad32Bit()) {
name = System.getProperty(JACOB_DLL_NAME_X64);
} else if (resources != null && keys.contains(JACOB_DLL_NAME)) {
name = resources.getString(JACOB_DLL_NAME);
} else if (resources != null && keys.contains(JACOB_DLL_NAME_X86)
&& shouldLoad32Bit()) {
name = resources.getString(JACOB_DLL_NAME_X86);
} else if (resources != null && keys.contains(JACOB_DLL_NAME_X64)
&& !shouldLoad32Bit()) {
name = resources.getString(JACOB_DLL_NAME_X64);
} else {
// No alternate NAME or PATH was defined, so use the default.
// We will almost always end up here.
name = getPreferredDLLName();
}
JacobObject.debug("Loading library " + name
+ " using System.loadLibrary ");
// System.out.println("Loading " + name);
System.loadLibrary(name);
}
}
/**
* Developer note: This method MUST be synchronized with the DLL names
* created as part of the build process in build.xml
* <p>
* The DLL name is "jacob\<PLATFORM\>.release"
*
* @return the preferred name of the DLL adjusted for this platform and
* version without the ".dll" extension
*/
public static String getPreferredDLLName() {
if (shouldLoad32Bit()) {
return "jacob" + "-" + JacobReleaseInfo.getBuildVersion() + "-"
+ DLL_NAME_MODIFIER_32_BIT;
} else {
return "jacob" + "-" + JacobReleaseInfo.getBuildVersion() + "-"
+ DLL_NAME_MODIFIER_64_BIT;
}
}
/**
* Detects whether this is a 32-bit JVM.
*
* @return {@code true} if this is a 32-bit JVM.
*/
protected static boolean shouldLoad32Bit() {
// This guesses whether we are running 32 or 64 bit Java.
// This works for Sun and IBM JVMs version 5.0 or later.
// May need to be adjusted for non-Sun JVMs.
String bits = System.getProperty("sun.arch.data.model", "?");
if (bits.equals("32"))
return true;
else if (bits.equals("64"))
return false;
// this works for jRocket
String arch = System.getProperty("java.vm.name", "?");
if (arch.toLowerCase().indexOf("64-bit") >= 0)
return false;
return true;
}
} // LibraryLoader

View File

@@ -1,29 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* We provide our own main sta thread to avoid COM tagging a random thread as
* the main STA - this is the thread in which all Apartment threaded components
* will be created if the client chooses an MTA threading model for the java
* side of the app.
*/
public class MainSTA extends STA {
}

View File

@@ -1,41 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* Thrown by java APIs that are not implemented either because they were never
* implemented or because they are being deprecated This is a subclass of
* ComException so callers can still just catch ComException.
*/
public class NotImplementedException extends JacobException {
/**
*
*/
private static final long serialVersionUID = -9169900832852356445L;
/**
* @param description
*/
public NotImplementedException(String description) {
super(description);
}
}

View File

@@ -1,279 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.WeakHashMap;
/**
* The Running Object Table (ROT) maps each thread to a collection of all the
* JacobObjects that were created in that thread. It always operates on the
* current thread so all the methods are static and they implicitly get the
* current thread.
* <p>
* The clearObjects method is used to release all the COM objects created by
* Jacob in the current thread prior to uninitializing COM for that thread.
* <p>
* Prior to 1.9, manual garbage collection was the only option in Jacob, but
* from 1.9 onward, setting the com.jacob.autogc system property allows the
* objects referenced by the ROT to be automatically GCed. Automatic GC may be
* preferable in systems with heavy event callbacks.
* <p>
* Is [ 1116101 ] jacob-msg 0284 relevant???
*/
public abstract class ROT {
/**
* Manual garbage collection was the only option pre 1.9 Can staticly cache
* the results because only one value and we don't let it change during a
* run
*/
protected static final boolean USE_AUTOMATIC_GARBAGE_COLLECTION = "true"
.equalsIgnoreCase(System.getProperty("com.jacob.autogc"));
/**
* If the code is ran from an applet that is called from javascript the Java
* Plugin does not give full permissions to the code and thus System
* properties cannot be accessed. They can be accessed at class
* initialization time.
*
* The default behavior is to include all classes in the ROT, setting a
* boolean here to indicate this prevents a call to System.getProperty as
* part of the general call flow.
*/
protected static final Boolean INCLUDE_ALL_CLASSES_IN_ROT = Boolean
.valueOf(System.getProperty("com.jacob.includeAllClassesInROT",
"true"));
/**
* Suffix added to class name to make up property name that determines if
* this object should be stored in the ROT. This 1.13 "feature" makes it
* possible to cause VariantViaEvent objects to not be added to the ROT in
* event callbacks.
* <p>
* We don't have a static for the actual property because there is a
* different property for each class that may make use of this feature.
*/
protected static String PUT_IN_ROT_SUFFIX = ".PutInROT";
/**
* A hash table where each element is another HashMap that represents a
* thread. Each thread HashMap contains the com objects created in that
* thread
*/
private static HashMap<String, Map<JacobObject, String>> rot = new HashMap<String, Map<JacobObject, String>>();
/**
* adds a new thread storage area to rot
*
* @return Map corresponding to the thread that this call was made in
*/
protected synchronized static Map<JacobObject, String> addThread() {
// should use the id here instead of the name because the name can be
// changed
String t_name = Thread.currentThread().getName();
if (rot.containsKey(t_name)) {
// nothing to do
} else {
Map<JacobObject, String> tab = null;
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ROT: Automatic GC flag == "
+ USE_AUTOMATIC_GARBAGE_COLLECTION);
}
if (!USE_AUTOMATIC_GARBAGE_COLLECTION) {
tab = new HashMap<JacobObject, String>();
} else {
tab = new WeakHashMap<JacobObject, String>();
}
rot.put(t_name, tab);
}
return getThreadObjects(false);
}
/**
* Returns the pool for this thread if it exists. can create a new one if
* you wish by passing in TRUE
*
* @param createIfDoesNotExist
* @return Map the collection that holds the objects created in the current
* thread
*/
protected synchronized static Map<JacobObject, String> getThreadObjects(
boolean createIfDoesNotExist) {
String t_name = Thread.currentThread().getName();
if (!rot.containsKey(t_name) && createIfDoesNotExist) {
addThread();
}
return rot.get(t_name);
}
/**
* Iterates across all of the entries in the Hashmap in the rot that
* corresponds to this thread. This calls safeRelease() on each entry and
* then clears the map when done and removes it from the rot. All traces of
* this thread's objects will disappear. This is called by COMThread in the
* tear down and provides a synchronous way of releasing memory
*/
protected static void clearObjects() {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ROT: " + rot.keySet().size()
+ " thread tables exist");
}
Map<JacobObject, String> tab = getThreadObjects(false);
if (tab != null) {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ROT: " + tab.keySet().size()
+ " objects to clear in this thread's ROT ");
}
// walk the values
Iterator<JacobObject> it = tab.keySet().iterator();
while (it.hasNext()) {
JacobObject o = it.next();
if (o != null
// can't use this cause creates a Variant if calling SafeAray
// and we get an exception modifying the collection while
// iterating
// && o.toString() != null
) {
if (JacobObject.isDebugEnabled()) {
if (o instanceof SafeArray) {
// SafeArray create more objects when calling
// toString()
// which causes a concurrent modification exception
// in HashMap
JacobObject.debug("ROT: removing "
+ o.getClass().getName());
} else {
// Variant toString() is probably always bad in here
JacobObject.debug("ROT: removing " + o.hashCode()
+ "->" + o.getClass().getName());
}
}
o.safeRelease();
}
}
// empty the collection
tab.clear();
// remove the collection from rot
ROT.removeThread();
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ROT: thread table cleared and removed");
}
} else {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ROT: nothing to clear!");
}
}
}
/**
* Removes the map from the rot that is associated with the current thread.
*/
private synchronized static void removeThread() {
// should this see if it exists first?
rot.remove(Thread.currentThread().getName());
}
/**
* @deprecated the java model leave the responsibility of clearing up
* objects to the Garbage Collector. Our programming model
* should not require that the user specifically remove object
* from the thread. <br>
* This will remove an object from the ROT <br>
* This does not need to be synchronized because only the rot
* modification related methods need to synchronized. Each
* individual map is only modified in a single thread.
* @param o
*/
@Deprecated
protected static void removeObject(JacobObject o) {
Map<JacobObject, String> tab = ROT.getThreadObjects(false);
if (tab != null) {
tab.remove(o);
}
o.safeRelease();
}
/**
* Adds an object to the HashMap for the current thread. <br>
* <p>
* This method does not need to be threaded because the only concurrent
* modification risk is on the hash map that contains all of the thread
* related hash maps. The individual thread related maps are only used on a
* per thread basis so there isn't a locking issue.
* <p>
* In addition, this method cannot be threaded because it calls
* ComThread.InitMTA. The ComThread object has some methods that call ROT so
* we could end up deadlocked. This method should be safe without the
* synchronization because the ROT works on per thread basis and the methods
* that add threads and remove thread related entries are all synchronized
*
*
* @param o
*/
protected static void addObject(JacobObject o) {
String shouldIncludeClassInROT = "true";
// only call System.getProperty if we are not including all classes in
// the ROT. This lets us run with standard Jacob behavior in Applets
// without the security exception raised by System.getProperty in the
// flow
if (!ROT.INCLUDE_ALL_CLASSES_IN_ROT) {
shouldIncludeClassInROT = System.getProperty(o.getClass().getName()
+ PUT_IN_ROT_SUFFIX, "true");
}
if (shouldIncludeClassInROT.equalsIgnoreCase("false")) {
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("JacobObject: New instance of "
+ o.getClass().getName() + " not added to ROT");
}
} else {
// first see if we have a table for this thread
Map<JacobObject, String> tab = getThreadObjects(false);
if (tab == null) {
// this thread has not been initialized as a COM thread
// so make it part of MTA for backwards compatibility
ComThread.InitMTA(false);
// don't really need the "true" because the InitMTA will have
// called back to the ROT to create a table for this thread
tab = getThreadObjects(true);
}
if (JacobObject.isDebugEnabled()) {
JacobObject.debug("ROT: adding " + o + "->"
+ o.getClass().getName()
+ " table size prior to addition:" + tab.size());
}
// add the object to the table that is specific to this thread
if (tab != null) {
tab.put(o, null);
}
}
}
/**
* ROT can't be a subclass of JacobObject because of the way ROT pools are
* managed so we force a DLL load here by referencing JacobObject
*/
static {
LibraryLoader.loadJacobLibrary();
}
}

View File

@@ -1,101 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* A class that implements a Single Threaded Apartment. Users will subclass this
* and override OnInit() and OnQuit() where they will create and destroy a COM
* component that wants to run in an STA other than the main STA.
*/
public class STA extends Thread {
/**
* referenced by STA.cpp
*/
public int threadID;
/**
* constructor for STA
*/
public STA() {
start(); // start the thread
}
/*
* (non-Javadoc)
*
* @see java.lang.Thread#run()
*/
public void run() {
// init COM
ComThread.InitSTA();
if (OnInit()) {
// this call blocks in the win32 message loop
// until quitMessagePump is called
doMessagePump();
}
OnQuit();
// uninit COM
ComThread.Release();
}
/**
* Override this method to create and initialize any COM component that you
* want to run in this thread. If anything fails, return false to terminate
* the thread.
*
* @return always returns true
*/
public boolean OnInit() {
return true;
}
/**
* Override this method to destroy any resource before the thread exits and
* COM in uninitialized
*/
public void OnQuit() {
// there is nothing to see here
}
/**
* calls quitMessagePump
*/
public void quit() {
quitMessagePump();
}
/**
* run a message pump for the main STA
*/
public native void doMessagePump();
/**
* quit message pump for the main STA
*/
public native void quitMessagePump();
/**
* STA isn't a subclass of JacobObject so a reference to it doesn't load the
* DLL without this
*/
static {
LibraryLoader.loadJacobLibrary();
}
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -1,502 +0,0 @@
/**
*
*/
package com.jacob.com;
import java.lang.reflect.Array;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.math.MathContext;
import java.util.Date;
/**
* A utility class used to convert between Java objects and Variants
*/
public final class VariantUtilities {
private VariantUtilities() {
// utility class with only static methods don't need constructors
}
/**
* Populates a variant object from a java object. This method attempts to
* figure out the appropriate Variant type
*
* @param targetVariant
* @param pValueObject
* @param fByRef
*/
protected static void populateVariant(Variant targetVariant,
Object pValueObject, boolean fByRef) {
if (pValueObject == null) {
targetVariant.putEmpty();
} else if (pValueObject instanceof Integer) {
if (fByRef) {
targetVariant.putIntRef(((Integer) pValueObject).intValue());
} else {
targetVariant.putInt(((Integer) pValueObject).intValue());
}
} else if (pValueObject instanceof Short) {
if (fByRef) {
targetVariant.putShortRef(((Short) pValueObject).shortValue());
} else {
targetVariant.putShort(((Short) pValueObject).shortValue());
}
} else if (pValueObject instanceof String) {
if (fByRef) {
targetVariant.putStringRef((String) pValueObject);
} else {
targetVariant.putString((String) pValueObject);
}
} else if (pValueObject instanceof Boolean) {
if (fByRef) {
targetVariant.putBooleanRef(((Boolean) pValueObject)
.booleanValue());
} else {
targetVariant.putBoolean(((Boolean) pValueObject)
.booleanValue());
}
} else if (pValueObject instanceof Double) {
if (fByRef) {
targetVariant.putDoubleRef(((Double) pValueObject)
.doubleValue());
} else {
targetVariant.putDouble(((Double) pValueObject).doubleValue());
}
} else if (pValueObject instanceof Float) {
if (fByRef) {
targetVariant.putFloatRef(((Float) pValueObject).floatValue());
} else {
targetVariant.putFloat(((Float) pValueObject).floatValue());
}
} else if (pValueObject instanceof BigDecimal) {
if (fByRef) {
targetVariant.putDecimalRef(((BigDecimal) pValueObject));
} else {
targetVariant.putDecimal(((BigDecimal) pValueObject));
}
} else if (pValueObject instanceof Byte) {
if (fByRef) {
targetVariant.putByteRef(((Byte) pValueObject).byteValue());
} else {
targetVariant.putByte(((Byte) pValueObject).byteValue());
}
} else if (pValueObject instanceof Date) {
if (fByRef) {
targetVariant.putDateRef((Date) pValueObject);
} else {
targetVariant.putDate((Date) pValueObject);
}
} else if (pValueObject instanceof Long) {
if (fByRef) {
targetVariant.putLongRef(((Long) pValueObject).longValue());
} else {
targetVariant.putLong(((Long) pValueObject).longValue());
}
} else if (pValueObject instanceof Currency) {
if (fByRef) {
targetVariant.putCurrencyRef(((Currency) pValueObject));
} else {
targetVariant.putCurrency(((Currency) pValueObject));
}
} else if (pValueObject instanceof SafeArray) {
if (fByRef) {
targetVariant.putSafeArrayRef((SafeArray) pValueObject);
} else {
targetVariant.putSafeArray((SafeArray) pValueObject);
}
} else if (pValueObject instanceof Dispatch) {
if (fByRef) {
targetVariant.putDispatchRef((Dispatch) pValueObject);
} else {
targetVariant.putDispatch((Dispatch) pValueObject);
}
} else if (pValueObject instanceof Variant) {
// newly added 1.12-pre6 to support VT_VARIANT
targetVariant.putVariant(pValueObject);
} else {
// sourceforge patch 2171967
// used to rely on coercion but sometimes crashed VM
throw new NotImplementedException(
"populateVariant() not implemented for "
+ pValueObject.getClass());
}
}
/**
* Map arguments based on msdn documentation. This method relies on the
* variant constructor except for arrays.
*
* @param objectToBeMadeIntoVariant
* @return Variant that represents the object
*/
protected static Variant objectToVariant(Object objectToBeMadeIntoVariant) {
if (objectToBeMadeIntoVariant == null) {
return new Variant();
} else if (objectToBeMadeIntoVariant instanceof Variant) {
// if a variant was passed in then be a slacker and just return it
return (Variant) objectToBeMadeIntoVariant;
} else if (objectToBeMadeIntoVariant.getClass().isArray()) {
// automatically convert arrays using reflection
// handle it differently based on the type of array
// added primitive support sourceforge 2762275
SafeArray sa = null;
int len1 = Array.getLength(objectToBeMadeIntoVariant);
Class componentType = objectToBeMadeIntoVariant.getClass()
.getComponentType();
if (componentType.isArray()) { // array of arrays
int max = 0;
for (int i = 0; i < len1; i++) {
Object e1 = Array.get(objectToBeMadeIntoVariant, i);
int len2 = Array.getLength(e1);
if (max < len2) {
max = len2;
}
}
sa = new SafeArray(Variant.VariantVariant, len1, max);
for (int i = 0; i < len1; i++) {
Object e1 = Array.get(objectToBeMadeIntoVariant, i);
for (int j = 0; j < Array.getLength(e1); j++) {
sa.setVariant(i, j, objectToVariant(Array.get(e1, j)));
}
}
} else if (byte.class.equals(componentType)) {
byte[] arr = (byte[]) objectToBeMadeIntoVariant;
sa = new SafeArray(Variant.VariantByte, len1);
for (int i = 0; i < len1; i++) {
sa.setByte(i, arr[i]);
}
} else if (int.class.equals(componentType)) {
int[] arr = (int[]) objectToBeMadeIntoVariant;
sa = new SafeArray(Variant.VariantInt, len1);
for (int i = 0; i < len1; i++) {
sa.setInt(i, arr[i]);
}
} else if (double.class.equals(componentType)) {
double[] arr = (double[]) objectToBeMadeIntoVariant;
sa = new SafeArray(Variant.VariantDouble, len1);
for (int i = 0; i < len1; i++) {
sa.setDouble(i, arr[i]);
}
} else if (long.class.equals(componentType)) {
long[] arr = (long[]) objectToBeMadeIntoVariant;
sa = new SafeArray(Variant.VariantLongInt, len1);
for (int i = 0; i < len1; i++) {
sa.setLong(i, arr[i]);
}
} else {
// array of object
sa = new SafeArray(Variant.VariantVariant, len1);
for (int i = 0; i < len1; i++) {
sa.setVariant(i, objectToVariant(Array.get(
objectToBeMadeIntoVariant, i)));
}
}
Variant returnVariant = new Variant();
populateVariant(returnVariant, sa, false);
return returnVariant;
} else {
// rely on populateVariant to throw an exception if its an
// invalid type
Variant returnVariant = new Variant();
populateVariant(returnVariant, objectToBeMadeIntoVariant, false);
return returnVariant;
}
}
/**
* converts an array of objects into an array of Variants by repeatedly
* calling obj2Variant(Object)
*
* @param arrayOfObjectsToBeConverted
* @return Variant[]
*/
protected static Variant[] objectsToVariants(
Object[] arrayOfObjectsToBeConverted) {
if (arrayOfObjectsToBeConverted instanceof Variant[]) {
// just return the passed in array if it is a Variant array
return (Variant[]) arrayOfObjectsToBeConverted;
} else {
Variant vArg[] = new Variant[arrayOfObjectsToBeConverted.length];
for (int i = 0; i < arrayOfObjectsToBeConverted.length; i++) {
vArg[i] = objectToVariant(arrayOfObjectsToBeConverted[i]);
}
return vArg;
}
}
/**
* Convert a JACOB Variant value to a Java object (type conversions).
* provided in Sourceforge feature request 959381. A fix was done to handle
* byRef bug report 1607878.
* <p>
* Unlike other toXXX() methods, it does not do a type conversion except for
* special data types (it shouldn't do any!)
* <p>
* Converts Variant.VariantArray types to SafeArrays
*
* @return Corresponding Java object of the type matching the Variant type.
* @throws IllegalStateException
* if no underlying windows data structure
* @throws NotImplementedException
* if unsupported conversion is requested
* @throws JacobException
* if the calculated result was a JacobObject usually as a
* result of error
*/
protected static Object variantToObject(Variant sourceData) {
Object result = null;
short type = sourceData.getvt(); // variant type
if ((type & Variant.VariantArray) == Variant.VariantArray) { // array
// returned?
SafeArray array = null;
type = (short) (type - Variant.VariantArray);
// From SF Bug 1840487
// This did call toSafeArray(false) but that meant
// this was the only variantToObject() that didn't have its own
// copy of the data so you would end up with weird run time
// errors after some GC. So now we just get stupid about it and
// always make a copy just like toSafeArray() does.
array = sourceData.toSafeArray();
result = array;
} else { // non-array object returned
switch (type) {
case Variant.VariantEmpty: // 0
case Variant.VariantNull: // 1
break;
case Variant.VariantShort: // 2
result = new Short(sourceData.getShort());
break;
case Variant.VariantShort | Variant.VariantByref: // 2
result = new Short(sourceData.getShortRef());
break;
case Variant.VariantInt: // 3
result = new Integer(sourceData.getInt());
break;
case Variant.VariantInt | Variant.VariantByref: // 3
result = new Integer(sourceData.getIntRef());
break;
case Variant.VariantFloat: // 4
result = new Float(sourceData.getFloat());
break;
case Variant.VariantFloat | Variant.VariantByref: // 4
result = new Float(sourceData.getFloatRef());
break;
case Variant.VariantDouble: // 5
result = new Double(sourceData.getDouble());
break;
case Variant.VariantDouble | Variant.VariantByref: // 5
result = new Double(sourceData.getDoubleRef());
break;
case Variant.VariantCurrency: // 6
result = sourceData.getCurrency();
break;
case Variant.VariantCurrency | Variant.VariantByref: // 6
result = sourceData.getCurrencyRef();
break;
case Variant.VariantDate: // 7
result = sourceData.getJavaDate();
break;
case Variant.VariantDate | Variant.VariantByref: // 7
result = sourceData.getJavaDateRef();
break;
case Variant.VariantString: // 8
result = sourceData.getString();
break;
case Variant.VariantString | Variant.VariantByref: // 8
result = sourceData.getStringRef();
break;
case Variant.VariantDispatch: // 9
result = sourceData.getDispatch();
break;
case Variant.VariantDispatch | Variant.VariantByref: // 9
result = sourceData.getDispatchRef(); // Can dispatches even
// be byRef?
break;
case Variant.VariantError: // 10
result = new NotImplementedException(
"toJavaObject() Not implemented for VariantError");
break;
case Variant.VariantBoolean: // 11
result = new Boolean(sourceData.getBoolean());
break;
case Variant.VariantBoolean | Variant.VariantByref: // 11
result = new Boolean(sourceData.getBooleanRef());
break;
case Variant.VariantVariant: // 12 they are always by ref
result = new NotImplementedException(
"toJavaObject() Not implemented for VariantVariant without ByRef");
break;
case Variant.VariantVariant | Variant.VariantByref: // 12
result = sourceData.getVariant();
break;
case Variant.VariantObject: // 13
result = new NotImplementedException(
"toJavaObject() Not implemented for VariantObject");
break;
case Variant.VariantDecimal: // 14
result = sourceData.getDecimal();
break;
case Variant.VariantDecimal | Variant.VariantByref: // 14
result = sourceData.getDecimalRef();
break;
case Variant.VariantByte: // 17
result = new Byte(sourceData.getByte());
break;
case Variant.VariantByte | Variant.VariantByref: // 17
result = new Byte(sourceData.getByteRef());
break;
case Variant.VariantLongInt: // 20
result = new Long(sourceData.getLong());
break;
case Variant.VariantLongInt | Variant.VariantByref: // 20
result = new Long(sourceData.getLongRef());
break;
case Variant.VariantTypeMask: // 4095
result = new NotImplementedException(
"toJavaObject() Not implemented for VariantBstrBlob/VariantTypeMask");
break;
case Variant.VariantArray: // 8192
result = new NotImplementedException(
"toJavaObject() Not implemented for VariantArray");
break;
case Variant.VariantByref: // 16384
result = new NotImplementedException(
"toJavaObject() Not implemented for VariantByref");
break;
default:
result = new NotImplementedException("Unknown return type: "
+ type);
// there was a "return result" here that caused defect 1602118
// so it was removed
break;
}// switch (type)
if (result instanceof JacobException) {
throw (JacobException) result;
}
}
return result;
}// toJava()
/**
* Verifies that we have a scale 0 <= x <= 28 and now more than 96 bits of
* data. The roundToMSDecimal method will attempt to adjust a BigDecimal to
* pass this set of tests
*
* @param in
* @throws IllegalArgumentException
* if out of bounds
*/
protected static void validateDecimalScaleAndBits(BigDecimal in) {
BigInteger allWordBigInt = in.unscaledValue();
if (in.scale() > 28) {
// should this cast to a string and call putStringRef()?
throw new IllegalArgumentException(
"VT_DECIMAL only supports a maximum scale of 28 and the passed"
+ " in value has a scale of " + in.scale());
} else if (in.scale() < 0) {
// should this cast to a string and call putStringRef()?
throw new IllegalArgumentException(
"VT_DECIMAL only supports a minimum scale of 0 and the passed"
+ " in value has a scale of " + in.scale());
} else if (allWordBigInt.bitLength() > 12 * 8) {
throw new IllegalArgumentException(
"VT_DECIMAL supports a maximum of "
+ 12
* 8
+ " bits not counting scale and the number passed in has "
+ allWordBigInt.bitLength());
} else {
// no bounds problem to be handled
}
}
/**
* Largest possible number with scale set to 0
*/
private static final BigDecimal LARGEST_DECIMAL = new BigDecimal(
new BigInteger("ffffffffffffffffffffffff", 16));
/**
* Smallest possible number with scale set to 0. MS doesn't support negative
* scales like BigDecimal.
*/
private static final BigDecimal SMALLEST_DECIMAL = new BigDecimal(
new BigInteger("ffffffffffffffffffffffff", 16).negate());
/**
* Does any validation that couldn't have been fixed by rounding or scale
* modification.
*
* @param in
* The BigDecimal to be validated
* @throws IllegalArgumentException
* if the number is too large or too small or null
*/
protected static void validateDecimalMinMax(BigDecimal in) {
if (in == null) {
throw new IllegalArgumentException(
"null is not a supported Decimal value.");
} else if (LARGEST_DECIMAL.compareTo(in) < 0) {
throw new IllegalArgumentException(
"Value too large for VT_DECIMAL data type:" + in.toString()
+ " integer: " + in.toBigInteger().toString(16)
+ " scale: " + in.scale());
} else if (SMALLEST_DECIMAL.compareTo(in) > 0) {
throw new IllegalArgumentException(
"Value too small for VT_DECIMAL data type:" + in.toString()
+ " integer: " + in.toBigInteger().toString(16)
+ " scale: " + in.scale());
}
}
/**
* Rounds the scale and bit length so that it will pass
* validateDecimalScaleBits(). Developers should call this method if they
* really want MS Decimal and don't want to lose precision.
* <p>
* Changing the scale on a number that can fit in an MS Decimal can change
* the number's representation enough that it will round to a number too
* large to be represented by an MS VT_DECIMAL
*
* @param sourceDecimal
* @return BigDecimal a new big decimal that was rounded to fit in an MS
* VT_DECIMAL
*/
public static BigDecimal roundToMSDecimal(BigDecimal sourceDecimal) {
BigInteger sourceDecimalIntComponent = sourceDecimal.unscaledValue();
BigDecimal destinationDecimal = new BigDecimal(
sourceDecimalIntComponent, sourceDecimal.scale());
int roundingModel = BigDecimal.ROUND_HALF_UP;
validateDecimalMinMax(destinationDecimal);
// First limit the number of digits and then the precision.
// Try and round to 29 digits because we can sometimes do that
BigInteger allWordBigInt;
allWordBigInt = destinationDecimal.unscaledValue();
if (allWordBigInt.bitLength() > 96) {
destinationDecimal = destinationDecimal.round(new MathContext(29));
// see if 29 digits uses more than 96 bits
if (allWordBigInt.bitLength() > 96) {
// Dang. It was over 97 bits so shorten it one more digit to
// stay <= 96 bits
destinationDecimal = destinationDecimal.round(new MathContext(
28));
}
}
// the bit manipulations above may change the scale so do it afterwards
// round the scale to the max MS can support
if (destinationDecimal.scale() > 28) {
destinationDecimal = destinationDecimal.setScale(28, roundingModel);
}
if (destinationDecimal.scale() < 0) {
destinationDecimal = destinationDecimal.setScale(0, roundingModel);
}
return destinationDecimal;
}
}

View File

@@ -1,34 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* a public class to variant that is used to track which variant objects are
* created by event callbacks This is solely used for that purpose.
*/
public class VariantViaEvent extends Variant {
/**
* Standard constructor used by JNI event handling layer
*/
public VariantViaEvent() {
super();
}
}

View File

@@ -1,47 +0,0 @@
/*
* Copyright (c) 1999-2004 Sourceforge JACOB Project.
* All rights reserved. Originator: Dan Adler (http://danadler.com).
* Get more information about JACOB at http://sourceforge.net/projects/jacob-project
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
package com.jacob.com;
/**
* thrown in util.cpp
*/
public class WrongThreadException extends JacobException {
/**
* identifier generated by Eclipse
*/
private static final long serialVersionUID = 6308780364980228692L;
/**
* standard 0 arg constructor with no message
*
*/
public WrongThreadException() {
super("No Message Provided.");
}
/**
* standard constructor with a string message
*
* @param s
*/
public WrongThreadException(String s) {
super(s);
}
}

View File

@@ -1,523 +0,0 @@
/*
* %W% %E%
*
* Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*
*/
#ifndef CLASSFILE_CONSTANTS_H
#define CLASSFILE_CONSTANTS_H
#ifdef __cplusplus
extern "C" {
#endif
/* Flags */
enum {
JVM_ACC_PUBLIC = 0x0001,
JVM_ACC_PRIVATE = 0x0002,
JVM_ACC_PROTECTED = 0x0004,
JVM_ACC_STATIC = 0x0008,
JVM_ACC_FINAL = 0x0010,
JVM_ACC_SYNCHRONIZED = 0x0020,
JVM_ACC_SUPER = 0x0020,
JVM_ACC_VOLATILE = 0x0040,
JVM_ACC_BRIDGE = 0x0040,
JVM_ACC_TRANSIENT = 0x0080,
JVM_ACC_VARARGS = 0x0080,
JVM_ACC_NATIVE = 0x0100,
JVM_ACC_INTERFACE = 0x0200,
JVM_ACC_ABSTRACT = 0x0400,
JVM_ACC_STRICT = 0x0800,
JVM_ACC_SYNTHETIC = 0x1000,
JVM_ACC_ANNOTATION = 0x2000,
JVM_ACC_ENUM = 0x4000
};
/* Used in newarray instruction. */
enum {
JVM_T_BOOLEAN = 4,
JVM_T_CHAR = 5,
JVM_T_FLOAT = 6,
JVM_T_DOUBLE = 7,
JVM_T_BYTE = 8,
JVM_T_SHORT = 9,
JVM_T_INT = 10,
JVM_T_LONG = 11
};
/* Constant Pool Entries */
enum {
JVM_CONSTANT_Utf8 = 1,
JVM_CONSTANT_Unicode = 2, /* unused */
JVM_CONSTANT_Integer = 3,
JVM_CONSTANT_Float = 4,
JVM_CONSTANT_Long = 5,
JVM_CONSTANT_Double = 6,
JVM_CONSTANT_Class = 7,
JVM_CONSTANT_String = 8,
JVM_CONSTANT_Fieldref = 9,
JVM_CONSTANT_Methodref = 10,
JVM_CONSTANT_InterfaceMethodref = 11,
JVM_CONSTANT_NameAndType = 12
};
/* StackMapTable type item numbers */
enum {
JVM_ITEM_Top = 0,
JVM_ITEM_Integer = 1,
JVM_ITEM_Float = 2,
JVM_ITEM_Double = 3,
JVM_ITEM_Long = 4,
JVM_ITEM_Null = 5,
JVM_ITEM_UninitializedThis = 6,
JVM_ITEM_Object = 7,
JVM_ITEM_Uninitialized = 8
};
/* Type signatures */
enum {
JVM_SIGNATURE_ARRAY = '[',
JVM_SIGNATURE_BYTE = 'B',
JVM_SIGNATURE_CHAR = 'C',
JVM_SIGNATURE_CLASS = 'L',
JVM_SIGNATURE_ENDCLASS = ';',
JVM_SIGNATURE_ENUM = 'E',
JVM_SIGNATURE_FLOAT = 'F',
JVM_SIGNATURE_DOUBLE = 'D',
JVM_SIGNATURE_FUNC = '(',
JVM_SIGNATURE_ENDFUNC = ')',
JVM_SIGNATURE_INT = 'I',
JVM_SIGNATURE_LONG = 'J',
JVM_SIGNATURE_SHORT = 'S',
JVM_SIGNATURE_VOID = 'V',
JVM_SIGNATURE_BOOLEAN = 'Z'
};
/* Opcodes */
enum {
JVM_OPC_nop = 0,
JVM_OPC_aconst_null = 1,
JVM_OPC_iconst_m1 = 2,
JVM_OPC_iconst_0 = 3,
JVM_OPC_iconst_1 = 4,
JVM_OPC_iconst_2 = 5,
JVM_OPC_iconst_3 = 6,
JVM_OPC_iconst_4 = 7,
JVM_OPC_iconst_5 = 8,
JVM_OPC_lconst_0 = 9,
JVM_OPC_lconst_1 = 10,
JVM_OPC_fconst_0 = 11,
JVM_OPC_fconst_1 = 12,
JVM_OPC_fconst_2 = 13,
JVM_OPC_dconst_0 = 14,
JVM_OPC_dconst_1 = 15,
JVM_OPC_bipush = 16,
JVM_OPC_sipush = 17,
JVM_OPC_ldc = 18,
JVM_OPC_ldc_w = 19,
JVM_OPC_ldc2_w = 20,
JVM_OPC_iload = 21,
JVM_OPC_lload = 22,
JVM_OPC_fload = 23,
JVM_OPC_dload = 24,
JVM_OPC_aload = 25,
JVM_OPC_iload_0 = 26,
JVM_OPC_iload_1 = 27,
JVM_OPC_iload_2 = 28,
JVM_OPC_iload_3 = 29,
JVM_OPC_lload_0 = 30,
JVM_OPC_lload_1 = 31,
JVM_OPC_lload_2 = 32,
JVM_OPC_lload_3 = 33,
JVM_OPC_fload_0 = 34,
JVM_OPC_fload_1 = 35,
JVM_OPC_fload_2 = 36,
JVM_OPC_fload_3 = 37,
JVM_OPC_dload_0 = 38,
JVM_OPC_dload_1 = 39,
JVM_OPC_dload_2 = 40,
JVM_OPC_dload_3 = 41,
JVM_OPC_aload_0 = 42,
JVM_OPC_aload_1 = 43,
JVM_OPC_aload_2 = 44,
JVM_OPC_aload_3 = 45,
JVM_OPC_iaload = 46,
JVM_OPC_laload = 47,
JVM_OPC_faload = 48,
JVM_OPC_daload = 49,
JVM_OPC_aaload = 50,
JVM_OPC_baload = 51,
JVM_OPC_caload = 52,
JVM_OPC_saload = 53,
JVM_OPC_istore = 54,
JVM_OPC_lstore = 55,
JVM_OPC_fstore = 56,
JVM_OPC_dstore = 57,
JVM_OPC_astore = 58,
JVM_OPC_istore_0 = 59,
JVM_OPC_istore_1 = 60,
JVM_OPC_istore_2 = 61,
JVM_OPC_istore_3 = 62,
JVM_OPC_lstore_0 = 63,
JVM_OPC_lstore_1 = 64,
JVM_OPC_lstore_2 = 65,
JVM_OPC_lstore_3 = 66,
JVM_OPC_fstore_0 = 67,
JVM_OPC_fstore_1 = 68,
JVM_OPC_fstore_2 = 69,
JVM_OPC_fstore_3 = 70,
JVM_OPC_dstore_0 = 71,
JVM_OPC_dstore_1 = 72,
JVM_OPC_dstore_2 = 73,
JVM_OPC_dstore_3 = 74,
JVM_OPC_astore_0 = 75,
JVM_OPC_astore_1 = 76,
JVM_OPC_astore_2 = 77,
JVM_OPC_astore_3 = 78,
JVM_OPC_iastore = 79,
JVM_OPC_lastore = 80,
JVM_OPC_fastore = 81,
JVM_OPC_dastore = 82,
JVM_OPC_aastore = 83,
JVM_OPC_bastore = 84,
JVM_OPC_castore = 85,
JVM_OPC_sastore = 86,
JVM_OPC_pop = 87,
JVM_OPC_pop2 = 88,
JVM_OPC_dup = 89,
JVM_OPC_dup_x1 = 90,
JVM_OPC_dup_x2 = 91,
JVM_OPC_dup2 = 92,
JVM_OPC_dup2_x1 = 93,
JVM_OPC_dup2_x2 = 94,
JVM_OPC_swap = 95,
JVM_OPC_iadd = 96,
JVM_OPC_ladd = 97,
JVM_OPC_fadd = 98,
JVM_OPC_dadd = 99,
JVM_OPC_isub = 100,
JVM_OPC_lsub = 101,
JVM_OPC_fsub = 102,
JVM_OPC_dsub = 103,
JVM_OPC_imul = 104,
JVM_OPC_lmul = 105,
JVM_OPC_fmul = 106,
JVM_OPC_dmul = 107,
JVM_OPC_idiv = 108,
JVM_OPC_ldiv = 109,
JVM_OPC_fdiv = 110,
JVM_OPC_ddiv = 111,
JVM_OPC_irem = 112,
JVM_OPC_lrem = 113,
JVM_OPC_frem = 114,
JVM_OPC_drem = 115,
JVM_OPC_ineg = 116,
JVM_OPC_lneg = 117,
JVM_OPC_fneg = 118,
JVM_OPC_dneg = 119,
JVM_OPC_ishl = 120,
JVM_OPC_lshl = 121,
JVM_OPC_ishr = 122,
JVM_OPC_lshr = 123,
JVM_OPC_iushr = 124,
JVM_OPC_lushr = 125,
JVM_OPC_iand = 126,
JVM_OPC_land = 127,
JVM_OPC_ior = 128,
JVM_OPC_lor = 129,
JVM_OPC_ixor = 130,
JVM_OPC_lxor = 131,
JVM_OPC_iinc = 132,
JVM_OPC_i2l = 133,
JVM_OPC_i2f = 134,
JVM_OPC_i2d = 135,
JVM_OPC_l2i = 136,
JVM_OPC_l2f = 137,
JVM_OPC_l2d = 138,
JVM_OPC_f2i = 139,
JVM_OPC_f2l = 140,
JVM_OPC_f2d = 141,
JVM_OPC_d2i = 142,
JVM_OPC_d2l = 143,
JVM_OPC_d2f = 144,
JVM_OPC_i2b = 145,
JVM_OPC_i2c = 146,
JVM_OPC_i2s = 147,
JVM_OPC_lcmp = 148,
JVM_OPC_fcmpl = 149,
JVM_OPC_fcmpg = 150,
JVM_OPC_dcmpl = 151,
JVM_OPC_dcmpg = 152,
JVM_OPC_ifeq = 153,
JVM_OPC_ifne = 154,
JVM_OPC_iflt = 155,
JVM_OPC_ifge = 156,
JVM_OPC_ifgt = 157,
JVM_OPC_ifle = 158,
JVM_OPC_if_icmpeq = 159,
JVM_OPC_if_icmpne = 160,
JVM_OPC_if_icmplt = 161,
JVM_OPC_if_icmpge = 162,
JVM_OPC_if_icmpgt = 163,
JVM_OPC_if_icmple = 164,
JVM_OPC_if_acmpeq = 165,
JVM_OPC_if_acmpne = 166,
JVM_OPC_goto = 167,
JVM_OPC_jsr = 168,
JVM_OPC_ret = 169,
JVM_OPC_tableswitch = 170,
JVM_OPC_lookupswitch = 171,
JVM_OPC_ireturn = 172,
JVM_OPC_lreturn = 173,
JVM_OPC_freturn = 174,
JVM_OPC_dreturn = 175,
JVM_OPC_areturn = 176,
JVM_OPC_return = 177,
JVM_OPC_getstatic = 178,
JVM_OPC_putstatic = 179,
JVM_OPC_getfield = 180,
JVM_OPC_putfield = 181,
JVM_OPC_invokevirtual = 182,
JVM_OPC_invokespecial = 183,
JVM_OPC_invokestatic = 184,
JVM_OPC_invokeinterface = 185,
JVM_OPC_xxxunusedxxx = 186,
JVM_OPC_new = 187,
JVM_OPC_newarray = 188,
JVM_OPC_anewarray = 189,
JVM_OPC_arraylength = 190,
JVM_OPC_athrow = 191,
JVM_OPC_checkcast = 192,
JVM_OPC_instanceof = 193,
JVM_OPC_monitorenter = 194,
JVM_OPC_monitorexit = 195,
JVM_OPC_wide = 196,
JVM_OPC_multianewarray = 197,
JVM_OPC_ifnull = 198,
JVM_OPC_ifnonnull = 199,
JVM_OPC_goto_w = 200,
JVM_OPC_jsr_w = 201,
JVM_OPC_MAX = 201
};
/* Opcode length initializer, use with something like:
* unsigned char opcode_length[JVM_OPC_MAX+1] = JVM_OPCODE_LENGTH_INITIALIZER;
*/
#define JVM_OPCODE_LENGTH_INITIALIZER { \
1, /* nop */ \
1, /* aconst_null */ \
1, /* iconst_m1 */ \
1, /* iconst_0 */ \
1, /* iconst_1 */ \
1, /* iconst_2 */ \
1, /* iconst_3 */ \
1, /* iconst_4 */ \
1, /* iconst_5 */ \
1, /* lconst_0 */ \
1, /* lconst_1 */ \
1, /* fconst_0 */ \
1, /* fconst_1 */ \
1, /* fconst_2 */ \
1, /* dconst_0 */ \
1, /* dconst_1 */ \
2, /* bipush */ \
3, /* sipush */ \
2, /* ldc */ \
3, /* ldc_w */ \
3, /* ldc2_w */ \
2, /* iload */ \
2, /* lload */ \
2, /* fload */ \
2, /* dload */ \
2, /* aload */ \
1, /* iload_0 */ \
1, /* iload_1 */ \
1, /* iload_2 */ \
1, /* iload_3 */ \
1, /* lload_0 */ \
1, /* lload_1 */ \
1, /* lload_2 */ \
1, /* lload_3 */ \
1, /* fload_0 */ \
1, /* fload_1 */ \
1, /* fload_2 */ \
1, /* fload_3 */ \
1, /* dload_0 */ \
1, /* dload_1 */ \
1, /* dload_2 */ \
1, /* dload_3 */ \
1, /* aload_0 */ \
1, /* aload_1 */ \
1, /* aload_2 */ \
1, /* aload_3 */ \
1, /* iaload */ \
1, /* laload */ \
1, /* faload */ \
1, /* daload */ \
1, /* aaload */ \
1, /* baload */ \
1, /* caload */ \
1, /* saload */ \
2, /* istore */ \
2, /* lstore */ \
2, /* fstore */ \
2, /* dstore */ \
2, /* astore */ \
1, /* istore_0 */ \
1, /* istore_1 */ \
1, /* istore_2 */ \
1, /* istore_3 */ \
1, /* lstore_0 */ \
1, /* lstore_1 */ \
1, /* lstore_2 */ \
1, /* lstore_3 */ \
1, /* fstore_0 */ \
1, /* fstore_1 */ \
1, /* fstore_2 */ \
1, /* fstore_3 */ \
1, /* dstore_0 */ \
1, /* dstore_1 */ \
1, /* dstore_2 */ \
1, /* dstore_3 */ \
1, /* astore_0 */ \
1, /* astore_1 */ \
1, /* astore_2 */ \
1, /* astore_3 */ \
1, /* iastore */ \
1, /* lastore */ \
1, /* fastore */ \
1, /* dastore */ \
1, /* aastore */ \
1, /* bastore */ \
1, /* castore */ \
1, /* sastore */ \
1, /* pop */ \
1, /* pop2 */ \
1, /* dup */ \
1, /* dup_x1 */ \
1, /* dup_x2 */ \
1, /* dup2 */ \
1, /* dup2_x1 */ \
1, /* dup2_x2 */ \
1, /* swap */ \
1, /* iadd */ \
1, /* ladd */ \
1, /* fadd */ \
1, /* dadd */ \
1, /* isub */ \
1, /* lsub */ \
1, /* fsub */ \
1, /* dsub */ \
1, /* imul */ \
1, /* lmul */ \
1, /* fmul */ \
1, /* dmul */ \
1, /* idiv */ \
1, /* ldiv */ \
1, /* fdiv */ \
1, /* ddiv */ \
1, /* irem */ \
1, /* lrem */ \
1, /* frem */ \
1, /* drem */ \
1, /* ineg */ \
1, /* lneg */ \
1, /* fneg */ \
1, /* dneg */ \
1, /* ishl */ \
1, /* lshl */ \
1, /* ishr */ \
1, /* lshr */ \
1, /* iushr */ \
1, /* lushr */ \
1, /* iand */ \
1, /* land */ \
1, /* ior */ \
1, /* lor */ \
1, /* ixor */ \
1, /* lxor */ \
3, /* iinc */ \
1, /* i2l */ \
1, /* i2f */ \
1, /* i2d */ \
1, /* l2i */ \
1, /* l2f */ \
1, /* l2d */ \
1, /* f2i */ \
1, /* f2l */ \
1, /* f2d */ \
1, /* d2i */ \
1, /* d2l */ \
1, /* d2f */ \
1, /* i2b */ \
1, /* i2c */ \
1, /* i2s */ \
1, /* lcmp */ \
1, /* fcmpl */ \
1, /* fcmpg */ \
1, /* dcmpl */ \
1, /* dcmpg */ \
3, /* ifeq */ \
3, /* ifne */ \
3, /* iflt */ \
3, /* ifge */ \
3, /* ifgt */ \
3, /* ifle */ \
3, /* if_icmpeq */ \
3, /* if_icmpne */ \
3, /* if_icmplt */ \
3, /* if_icmpge */ \
3, /* if_icmpgt */ \
3, /* if_icmple */ \
3, /* if_acmpeq */ \
3, /* if_acmpne */ \
3, /* goto */ \
3, /* jsr */ \
2, /* ret */ \
99, /* tableswitch */ \
99, /* lookupswitch */ \
1, /* ireturn */ \
1, /* lreturn */ \
1, /* freturn */ \
1, /* dreturn */ \
1, /* areturn */ \
1, /* return */ \
3, /* getstatic */ \
3, /* putstatic */ \
3, /* getfield */ \
3, /* putfield */ \
3, /* invokevirtual */ \
3, /* invokespecial */ \
3, /* invokestatic */ \
5, /* invokeinterface */ \
0, /* xxxunusedxxx */ \
3, /* new */ \
2, /* newarray */ \
3, /* anewarray */ \
1, /* arraylength */ \
1, /* athrow */ \
3, /* checkcast */ \
3, /* instanceof */ \
1, /* monitorenter */ \
1, /* monitorexit */ \
0, /* wide */ \
4, /* multianewarray */ \
3, /* ifnull */ \
3, /* ifnonnull */ \
5, /* goto_w */ \
5 /* jsr_w */ \
}
#ifdef __cplusplus
} /* extern "C" */
#endif /* __cplusplus */
#endif /* CLASSFILE_CONSTANTS */

View File

@@ -1,278 +0,0 @@
/*
* %W% %E%
*
* Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/
#ifndef _JAVASOFT_JAWT_H_
#define _JAVASOFT_JAWT_H_
#include "jni.h"
#ifdef __cplusplus
extern "C" {
#endif
/*
* AWT native interface (new in JDK 1.3)
*
* The AWT native interface allows a native C or C++ application a means
* by which to access native structures in AWT. This is to facilitate moving
* legacy C and C++ applications to Java and to target the needs of the
* community who, at present, wish to do their own native rendering to canvases
* for performance reasons. Standard extensions such as Java3D also require a
* means to access the underlying native data structures of AWT.
*
* There may be future extensions to this API depending on demand.
*
* A VM does not have to implement this API in order to pass the JCK.
* It is recommended, however, that this API is implemented on VMs that support
* standard extensions, such as Java3D.
*
* Since this is a native API, any program which uses it cannot be considered
* 100% pure java.
*/
/*
* AWT Native Drawing Surface (JAWT_DrawingSurface).
*
* For each platform, there is a native drawing surface structure. This
* platform-specific structure can be found in jawt_md.h. It is recommended
* that additional platforms follow the same model. It is also recommended
* that VMs on Win32 and Solaris support the existing structures in jawt_md.h.
*
*******************
* EXAMPLE OF USAGE:
*******************
*
* In Win32, a programmer wishes to access the HWND of a canvas to perform
* native rendering into it. The programmer has declared the paint() method
* for their canvas subclass to be native:
*
*
* MyCanvas.java:
*
* import java.awt.*;
*
* public class MyCanvas extends Canvas {
*
* static {
* System.loadLibrary("mylib");
* }
*
* public native void paint(Graphics g);
* }
*
*
* myfile.c:
*
* #include "jawt_md.h"
* #include <assert.h>
*
* JNIEXPORT void JNICALL
* Java_MyCanvas_paint(JNIEnv* env, jobject canvas, jobject graphics)
* {
* JAWT awt;
* JAWT_DrawingSurface* ds;
* JAWT_DrawingSurfaceInfo* dsi;
* JAWT_Win32DrawingSurfaceInfo* dsi_win;
* jboolean result;
* jint lock;
*
* // Get the AWT
* awt.version = JAWT_VERSION_1_3;
* result = JAWT_GetAWT(env, &awt);
* assert(result != JNI_FALSE);
*
* // Get the drawing surface
* ds = awt.GetDrawingSurface(env, canvas);
* assert(ds != NULL);
*
* // Lock the drawing surface
* lock = ds->Lock(ds);
* assert((lock & JAWT_LOCK_ERROR) == 0);
*
* // Get the drawing surface info
* dsi = ds->GetDrawingSurfaceInfo(ds);
*
* // Get the platform-specific drawing info
* dsi_win = (JAWT_Win32DrawingSurfaceInfo*)dsi->platformInfo;
*
* //////////////////////////////
* // !!! DO PAINTING HERE !!! //
* //////////////////////////////
*
* // Free the drawing surface info
* ds->FreeDrawingSurfaceInfo(dsi);
*
* // Unlock the drawing surface
* ds->Unlock(ds);
*
* // Free the drawing surface
* awt.FreeDrawingSurface(ds);
* }
*
*/
/*
* JAWT_Rectangle
* Structure for a native rectangle.
*/
typedef struct jawt_Rectangle {
jint x;
jint y;
jint width;
jint height;
} JAWT_Rectangle;
struct jawt_DrawingSurface;
/*
* JAWT_DrawingSurfaceInfo
* Structure for containing the underlying drawing information of a component.
*/
typedef struct jawt_DrawingSurfaceInfo {
/*
* Pointer to the platform-specific information. This can be safely
* cast to a JAWT_Win32DrawingSurfaceInfo on Windows or a
* JAWT_X11DrawingSurfaceInfo on Solaris. See jawt_md.h for details.
*/
void* platformInfo;
/* Cached pointer to the underlying drawing surface */
struct jawt_DrawingSurface* ds;
/* Bounding rectangle of the drawing surface */
JAWT_Rectangle bounds;
/* Number of rectangles in the clip */
jint clipSize;
/* Clip rectangle array */
JAWT_Rectangle* clip;
} JAWT_DrawingSurfaceInfo;
#define JAWT_LOCK_ERROR 0x00000001
#define JAWT_LOCK_CLIP_CHANGED 0x00000002
#define JAWT_LOCK_BOUNDS_CHANGED 0x00000004
#define JAWT_LOCK_SURFACE_CHANGED 0x00000008
/*
* JAWT_DrawingSurface
* Structure for containing the underlying drawing information of a component.
* All operations on a JAWT_DrawingSurface MUST be performed from the same
* thread as the call to GetDrawingSurface.
*/
typedef struct jawt_DrawingSurface {
/*
* Cached reference to the Java environment of the calling thread.
* If Lock(), Unlock(), GetDrawingSurfaceInfo() or
* FreeDrawingSurfaceInfo() are called from a different thread,
* this data member should be set before calling those functions.
*/
JNIEnv* env;
/* Cached reference to the target object */
jobject target;
/*
* Lock the surface of the target component for native rendering.
* When finished drawing, the surface must be unlocked with
* Unlock(). This function returns a bitmask with one or more of the
* following values:
*
* JAWT_LOCK_ERROR - When an error has occurred and the surface could not
* be locked.
*
* JAWT_LOCK_CLIP_CHANGED - When the clip region has changed.
*
* JAWT_LOCK_BOUNDS_CHANGED - When the bounds of the surface have changed.
*
* JAWT_LOCK_SURFACE_CHANGED - When the surface itself has changed
*/
jint (JNICALL *Lock)
(struct jawt_DrawingSurface* ds);
/*
* Get the drawing surface info.
* The value returned may be cached, but the values may change if
* additional calls to Lock() or Unlock() are made.
* Lock() must be called before this can return a valid value.
* Returns NULL if an error has occurred.
* When finished with the returned value, FreeDrawingSurfaceInfo must be
* called.
*/
JAWT_DrawingSurfaceInfo* (JNICALL *GetDrawingSurfaceInfo)
(struct jawt_DrawingSurface* ds);
/*
* Free the drawing surface info.
*/
void (JNICALL *FreeDrawingSurfaceInfo)
(JAWT_DrawingSurfaceInfo* dsi);
/*
* Unlock the drawing surface of the target component for native rendering.
*/
void (JNICALL *Unlock)
(struct jawt_DrawingSurface* ds);
} JAWT_DrawingSurface;
/*
* JAWT
* Structure for containing native AWT functions.
*/
typedef struct jawt {
/*
* Version of this structure. This must always be set before
* calling JAWT_GetAWT()
*/
jint version;
/*
* Return a drawing surface from a target jobject. This value
* may be cached.
* Returns NULL if an error has occurred.
* Target must be a java.awt.Component (should be a Canvas
* or Window for native rendering).
* FreeDrawingSurface() must be called when finished with the
* returned JAWT_DrawingSurface.
*/
JAWT_DrawingSurface* (JNICALL *GetDrawingSurface)
(JNIEnv* env, jobject target);
/*
* Free the drawing surface allocated in GetDrawingSurface.
*/
void (JNICALL *FreeDrawingSurface)
(JAWT_DrawingSurface* ds);
/*
* Since 1.4
* Locks the entire AWT for synchronization purposes
*/
void (JNICALL *Lock)(JNIEnv* env);
/*
* Since 1.4
* Unlocks the entire AWT for synchronization purposes
*/
void (JNICALL *Unlock)(JNIEnv* env);
/*
* Since 1.4
* Returns a reference to a java.awt.Component from a native
* platform handle. On Windows, this corresponds to an HWND;
* on Solaris and Linux, this is a Drawable. For other platforms,
* see the appropriate machine-dependent header file for a description.
* The reference returned by this function is a local
* reference that is only valid in this environment.
* This function returns a NULL reference if no component could be
* found with matching platform information.
*/
jobject (JNICALL *GetComponent)(JNIEnv* env, void* platformInfo);
} JAWT;
/*
* Get the AWT native structure. This function returns JNI_FALSE if
* an error occurs.
*/
_JNI_IMPORT_OR_EXPORT_
jboolean JNICALL JAWT_GetAWT(JNIEnv* env, JAWT* awt);
#define JAWT_VERSION_1_3 0x00010003
#define JAWT_VERSION_1_4 0x00010004
#ifdef __cplusplus
} /* extern "C" */
#endif
#endif /* !_JAVASOFT_JAWT_H_ */

View File

@@ -1,237 +0,0 @@
/*
* %W% %E%
*
* Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/
/*
* Java Debug Wire Protocol Transport Service Provider Interface.
*/
#ifndef JDWPTRANSPORT_H
#define JDWPTRANSPORT_H
#include "jni.h"
enum {
JDWPTRANSPORT_VERSION_1_0 = 0x00010000
};
#ifdef __cplusplus
extern "C" {
#endif
struct jdwpTransportNativeInterface_;
struct _jdwpTransportEnv;
#ifdef __cplusplus
typedef _jdwpTransportEnv jdwpTransportEnv;
#else
typedef const struct jdwpTransportNativeInterface_ *jdwpTransportEnv;
#endif /* __cplusplus */
/*
* Errors. Universal errors with JVMTI/JVMDI equivalents keep the
* values the same.
*/
typedef enum {
JDWPTRANSPORT_ERROR_NONE = 0,
JDWPTRANSPORT_ERROR_ILLEGAL_ARGUMENT = 103,
JDWPTRANSPORT_ERROR_OUT_OF_MEMORY = 110,
JDWPTRANSPORT_ERROR_INTERNAL = 113,
JDWPTRANSPORT_ERROR_ILLEGAL_STATE = 201,
JDWPTRANSPORT_ERROR_IO_ERROR = 202,
JDWPTRANSPORT_ERROR_TIMEOUT = 203,
JDWPTRANSPORT_ERROR_MSG_NOT_AVAILABLE = 204
} jdwpTransportError;
/*
* Structure to define capabilities
*/
typedef struct {
unsigned int can_timeout_attach :1;
unsigned int can_timeout_accept :1;
unsigned int can_timeout_handshake :1;
unsigned int reserved3 :1;
unsigned int reserved4 :1;
unsigned int reserved5 :1;
unsigned int reserved6 :1;
unsigned int reserved7 :1;
unsigned int reserved8 :1;
unsigned int reserved9 :1;
unsigned int reserved10 :1;
unsigned int reserved11 :1;
unsigned int reserved12 :1;
unsigned int reserved13 :1;
unsigned int reserved14 :1;
unsigned int reserved15 :1;
} JDWPTransportCapabilities;
/*
* Structures to define packet layout.
*
* See: http://java.sun.com/j2se/1.5/docs/guide/jpda/jdwp-spec.html
*/
enum {
JDWPTRANSPORT_FLAGS_NONE = 0x0,
JDWPTRANSPORT_FLAGS_REPLY = 0x80
};
typedef struct {
jint len;
jint id;
jbyte flags;
jbyte cmdSet;
jbyte cmd;
jbyte *data;
} jdwpCmdPacket;
typedef struct {
jint len;
jint id;
jbyte flags;
jshort errorCode;
jbyte *data;
} jdwpReplyPacket;
typedef struct {
union {
jdwpCmdPacket cmd;
jdwpReplyPacket reply;
} type;
} jdwpPacket;
/*
* JDWP functions called by the transport.
*/
typedef struct jdwpTransportCallback {
void *(*alloc)(jint numBytes); /* Call this for all allocations */
void (*free)(void *buffer); /* Call this for all deallocations */
} jdwpTransportCallback;
typedef jint (JNICALL *jdwpTransport_OnLoad_t)(JavaVM *jvm,
jdwpTransportCallback *callback,
jint version,
jdwpTransportEnv** env);
/* Function Interface */
struct jdwpTransportNativeInterface_ {
/* 1 : RESERVED */
void *reserved1;
/* 2 : Get Capabilities */
jdwpTransportError (JNICALL *GetCapabilities)(jdwpTransportEnv* env,
JDWPTransportCapabilities *capabilities_ptr);
/* 3 : Attach */
jdwpTransportError (JNICALL *Attach)(jdwpTransportEnv* env,
const char* address,
jlong attach_timeout,
jlong handshake_timeout);
/* 4: StartListening */
jdwpTransportError (JNICALL *StartListening)(jdwpTransportEnv* env,
const char* address,
char** actual_address);
/* 5: StopListening */
jdwpTransportError (JNICALL *StopListening)(jdwpTransportEnv* env);
/* 6: Accept */
jdwpTransportError (JNICALL *Accept)(jdwpTransportEnv* env,
jlong accept_timeout,
jlong handshake_timeout);
/* 7: IsOpen */
jboolean (JNICALL *IsOpen)(jdwpTransportEnv* env);
/* 8: Close */
jdwpTransportError (JNICALL *Close)(jdwpTransportEnv* env);
/* 9: ReadPacket */
jdwpTransportError (JNICALL *ReadPacket)(jdwpTransportEnv* env,
jdwpPacket *pkt);
/* 10: Write Packet */
jdwpTransportError (JNICALL *WritePacket)(jdwpTransportEnv* env,
const jdwpPacket* pkt);
/* 11: GetLastError */
jdwpTransportError (JNICALL *GetLastError)(jdwpTransportEnv* env,
char** error);
};
/*
* Use inlined functions so that C++ code can use syntax such as
* env->Attach("mymachine:5000", 10*1000, 0);
*
* rather than using C's :-
*
* (*env)->Attach(env, "mymachine:5000", 10*1000, 0);
*/
struct _jdwpTransportEnv {
const struct jdwpTransportNativeInterface_ *functions;
#ifdef __cplusplus
jdwpTransportError GetCapabilities(JDWPTransportCapabilities *capabilities_ptr) {
return functions->GetCapabilities(this, capabilities_ptr);
}
jdwpTransportError Attach(const char* address, jlong attach_timeout,
jlong handshake_timeout) {
return functions->Attach(this, address, attach_timeout, handshake_timeout);
}
jdwpTransportError StartListening(const char* address,
char** actual_address) {
return functions->StartListening(this, address, actual_address);
}
jdwpTransportError StopListening(void) {
return functions->StopListening(this);
}
jdwpTransportError Accept(jlong accept_timeout, jlong handshake_timeout) {
return functions->Accept(this, accept_timeout, handshake_timeout);
}
jboolean IsOpen(void) {
return functions->IsOpen(this);
}
jdwpTransportError Close(void) {
return functions->Close(this);
}
jdwpTransportError ReadPacket(jdwpPacket *pkt) {
return functions->ReadPacket(this, pkt);
}
jdwpTransportError WritePacket(const jdwpPacket* pkt) {
return functions->WritePacket(this, pkt);
}
jdwpTransportError GetLastError(char** error) {
return functions->GetLastError(this, error);
}
#endif /* __cplusplus */
};
#ifdef __cplusplus
} /* extern "C" */
#endif /* __cplusplus */
#endif /* JDWPTRANSPORT_H */

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -1,41 +0,0 @@
/*
* %W% %E%
*
* Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/
#ifndef _JAVASOFT_JAWT_MD_H_
#define _JAVASOFT_JAWT_MD_H_
#include <windows.h>
#include "jawt.h"
#ifdef __cplusplus
extern "C" {
#endif
/*
* Win32-specific declarations for AWT native interface.
* See notes in jawt.h for an example of use.
*/
typedef struct jawt_Win32DrawingSurfaceInfo {
/* Native window, DDB, or DIB handle */
union {
HWND hwnd;
HBITMAP hbitmap;
void* pbits;
};
/*
* This HDC should always be used instead of the HDC returned from
* BeginPaint() or any calls to GetDC().
*/
HDC hdc;
HPALETTE hpalette;
} JAWT_Win32DrawingSurfaceInfo;
#ifdef __cplusplus
}
#endif
#endif /* !_JAVASOFT_JAWT_MD_H_ */

View File

@@ -1,19 +0,0 @@
/*
* %W% %E%
*
* Copyright (c) 2006, Oracle and/or its affiliates. All rights reserved.
* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
*/
#ifndef _JAVASOFT_JNI_MD_H_
#define _JAVASOFT_JNI_MD_H_
#define JNIEXPORT __declspec(dllexport)
#define JNIIMPORT __declspec(dllimport)
#define JNICALL __stdcall
typedef long jint;
typedef __int64 jlong;
typedef signed char jbyte;
#endif /* !_JAVASOFT_JNI_MD_H_ */

Binary file not shown.