taksan / skype-java-api

Skype API for Java, based on Skype4Java library
128 stars 60 forks source link

OS X 64-bit support #25

Closed petergeneric closed 11 years ago

petergeneric commented 11 years ago

Hi,

I noticed that the latest version of Skype (6.1) for OS X includes a Skype.framework that's compiled for i386 and x86_64. I also needed to make a change to the CC variable in the Makefile to make it compile on my system (OS 10.8, Xcode 4.6) so I changed it to clang.

I'm not a native code guy so I'm not sure that I made this change in the best way possible... in particular the jnilib that comes out of clang references the Skype framework as @executablepath/../ which caused me some trouble - I had to call install_name_tool in the Makefile to make it point to the right place.

The unit tests don't succeed - calls like getVersion seem to fail - I don't know if this is a result of the changes I made or because Skype 6.1 behaves differently. There may be something more complicated going here that I'm not understanding

taksan commented 11 years ago

Hi

Have you tried running the tests before making your changes to check whether it the junit fails? You just need to make sure you're using java in 32bit compatibility mode.

Another problem: are your changes compatible with prior skypes? Have you checked? I'm worried it might break the compatibility... it might be better to split the native modules for 32bit and 64 bit and create the x86_64 jnilib from its module. In this case, I don't mind if doesn't work with older skypes as 64 bit, since it was already impossible anyway.

petergeneric commented 11 years ago

Hi,

I had didn't run them beforehand because I only had the Oracle JVM set up (it doesn't support 32-bit mode on OS X). I have switched back to the Apple 1.6 JVM and was able to get it to run in 32-bit mode.

Originally I had only tested with Skype 6.1.0.2295. I have now tested my changes with 5.1.0.968 and 6.2.0.1117. Under 6.x the tests fail because Skype.getVersion results in an Internal error (see the end of this comment).

I wrote a simple test:

Skype.setDebug(true);
Skype.setDebugNative(true);

Assert.assertTrue(Skype.isInstalled());

for (Chat chat: Skype.getAllChats()) {
    System.out.println(chat.getId());

    for (User user: chat.getAllMembers()) {
        System.out.println(user.getDisplayName());
    }
}

When run:

Skype Version Java Arch Skype.framework Result
6.2.0.1117 32/64 6.1.0.2295 Some functionality works, frequent ignored commands
6.1.0.2295 32/64 6.1.0.2295 Some functionality works, frequent ignored commands
5.1.0.968 32 6.1.0.2295 Works well
5.1.0.968 64 6.1.0.2295 Does not work (get CONNSTATUS ONLINE then nothing)

On 6.x this usually produces the following output (sometimes it gets a list of users - but then fetching the display name fails / returns nothing).

<- CONNSTATUS ONLINE
<- CURRENTUSERHANDLE my-skype-handle
<- USERSTATUS ONLINE
<- ERROR 9901 Internal error
-> SEARCH CHATS
<- CHATS #someuser/$someotheruser;somehex, #someuser/$someotheruser;somemorehex
-> GET CHAT #someuser/$someotheruser;somehex MEMBERS
-> GET CHAT #someuser/$someotheruser;somehex MEMBERS

com.skype.NotAttachedException
    at com.skype.Utils.convertToSkypeException(Utils.java:57)
    at com.skype.Chat.getUsersProperty(Chat.java:425)
    at com.skype.Chat.getAllMembers(Chat.java:340)
    at com.skype.SystemTest.testGetChats(SystemTest.java:38)
Caused by: com.skype.connector.NotAttachedException
    at com.skype.connector.Connector.execute(Connector.java:871)
    at com.skype.connector.Connector.execute(Connector.java:827)
    at com.skype.connector.Connector.execute(Connector.java:786)
    at com.skype.Chat.getUsersProperty(Chat.java:413)
    ... 27 more
Caused by: com.skype.connector.NotAttachedException
    at com.skype.connector.Connector$11.call(Connector.java:935)
    at com.skype.connector.Connector$11.call(Connector.java:907)
    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303)
    at java.util.concurrent.FutureTask.run(FutureTask.java:138)
    at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908)
    at java.lang.Thread.run(Thread.java:680)

Process finished with exit code 255

6.x calls to Skype.getVersion() always fail with:

<- CONNSTATUS ONLINE
-> GET SKYPEVERSION 
<- CURRENTUSERHANDLE my-skype-handle
<- USERSTATUS ONLINE
<- ERROR 9901 Internal error
<- ERROR 9901 Internal error

com.skype.CommandFailedException: Internal error
    at com.skype.Utils.checkError(Utils.java:77)
    at com.skype.Utils.getProperty(Utils.java:154)
    at com.skype.Skype.getVersion(Skype.java:147)
    at com.skype.SystemTest.testGetVersion(SystemTest.java:35)
AlexeyPirogov commented 11 years ago

Guys, I'm new to this lib, so short question. Should/can we expect supporting of OS X 64-bit in next a few months?

taksan commented 11 years ago

It seems there's something wrong with the 64bit library provided by skype that makes it imcompatible with the current native library.

I can't tell you for sure how long is it going to take until we can release this support. petergeneric was the only one taking a look on it, I still haven't checked it yet.

taksan commented 11 years ago

@petergeneric , this "ERROR 9901 Internal error" seems an error issued by skype itself. I still didn't check the 64bit skype library, but it usually has an example application that can be used to send hard coded commands. Have you tried use this application?

petergeneric commented 11 years ago

I downloaded the example but it's not been modified since 2005 (and requires PowerPC) so I suspect it will not be of any more help - I'll have a look at what happens when I issue the low-level API calls directly from Java

petergeneric commented 11 years ago

I've spent some time playing around with things this evening and have decided to close this pull request - I can't even reproduce the results of my table above using Skype 5.1 and 32-bit Java so it's possible something else is going on here - and I don't have the time to dedicate to figuring out what's going on (and if it is a problem with Skype, judging from their JIRA they won't fix it...)

If anyone else is interested in continuing here are the changes I made to the Makefile to get it to compile using clang (Apple clang version 4.0 (tags/Apple/clang-421.0.60) (based on LLVM 3.1svn) for the Skype.Framework in Skype 6.1 on OS X 10.8 and Xcode 4.6:

diff --git a/src-native/src_osx/Makefile b/src-native/src_osx/Makefile
index f0df474..9aaf919 100644
--- a/src-native/src_osx/Makefile
+++ b/src-native/src_osx/Makefile
@@ -21,7 +21,7 @@
 # * Gabriel Takeuchi - Removed need for project builder and xcode, builds now just using "make"
 # ******************************************************************************/

-ARCH=-arch i386 -arch ppc 
+ARCH=-arch i386 -arch x86_64 
 CWD=.
 JNILib=$(CWD)/build/skype.build/Release/JNILib.build
 OBJS_NORMAL=$(JNILib)/Objects-normal/
@@ -29,7 +29,7 @@ DERIVED_SRCS=$(JNILib)/DerivedSources
 RELEASE_DIR=$(CWD)/build/Release

 OBJ=$(OBJS_NORMAL)/SkypeFramework.o
-CC=/Developer/usr/bin/gcc-4.2 
+CC=clang
 LINK_FILELIST=$(OBJS_NORMAL)/skype.LinkFileList
 CC_FLAGS=-fmessage-length=0 -pipe -Wno-trigraphs -fpascal-strings -fasm-blocks -Os -Wunused-variable \
        -Wmost -Wno-four-char-constants -Wno-unknown-pragmas
@@ -51,6 +51,7 @@ all: $(TARGET)

 $(TARGET): mkdirs $(OBJ)
        $(CC) $(ARCH) -L$(RELEASE_DIR) $(F_DIR) -filelist $(LINK_FILELIST) $(FRAMEWORKS) $(INSTALL_FLAG) $(LD_FLAGS) -o $(TARGET)
+       install_name_tool -change "@executable_path/../Frameworks/Skype.framework/Versions/A/Skype" "@loader_path/Skype.Framework" $(TARGET)

 mkdirs: 
        mkdir -p $(DERIVED_SRCS)