~drgeo-developers/drgeo/trunk

« back to all changes in this revision

Viewing changes to VMs/iPad/source/iOS/plugins/SqueakObjectiveC/squeakProxy.m

  • Committer: Hilaire Fernandes
  • Date: 2012-01-27 21:15:40 UTC
  • Revision ID: hilaire.fernandes@gmail.com-20120127211540-912spf97bhpx6mve
Initial additions

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
//
 
2
//  squeakProxy.m
 
3
//  SqueakObjectiveC
 
4
//
 
5
//  Created by John M McIntosh on 01/02/09.
 
6
//  Copyright 2009 Corporate Smalltalk Consulting Ltd. All rights reserved.
 
7
 
 
8
/* 
 
9
 Some code from 
 
10
 http://www.squeaksource.com/ObjectiveCBridge.html
 
11
 developers and contributors 
 
12
 Creator:       Alain Fischer
 
13
 Admin: Avi Bryant, Alain Fischer
 
14
 Developer:     Todd Blanchard
 
15
 
 
16
 MIT License
 
17
 Permission is hereby granted, free of charge, to any person
 
18
 obtaining a copy of this software and associated documentation
 
19
 files (the "Software"), to deal in the Software without
 
20
 restriction, including without limitation the rights to use,
 
21
 copy, modify, merge, publish, distribute, sublicense, and/or sell 
 
22
 copies of the Software, and to permit persons to whom the
 
23
 Software is furnished to do so, subject to the following
 
24
 conditions:
 
25
 
 
26
 The above copyright notice and this permission notice shall be
 
27
 included in all copies or substantial portions of the Software.
 
28
 
 
29
 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 
30
 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
 
31
 OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
 
32
 NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 
33
 HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
 
34
 WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 
35
 FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 
36
 OTHER DEALINGS IN THE SOFTWARE.
 
37
 
 
38
 The end-user documentation included with the redistribution, if any, must include the following acknowledgment: 
 
39
 "This product includes software developed by Corporate Smalltalk Consulting Ltd (http://www.smalltalkconsulting.com) 
 
40
 and its contributors", in the same place and form as other third-party acknowledgments. 
 
41
 Alternately, this acknowledgment may appear in the software itself, in the same form and location as other 
 
42
 such third-party acknowledgments.
 
43
 */
 
44
//
 
45
 
 
46
#import "squeakProxy.h"
 
47
 
 
48
 
 
49
@implementation SqueakProxy
 
50
 
 
51
@synthesize sem;
 
52
@synthesize invocation;
 
53
@synthesize lockForSqueak;
 
54
@synthesize sigs;
 
55
@synthesize protocol;
 
56
@synthesize target;
 
57
@synthesize callbackid;
 
58
 
 
59
- (id) initWithSemaphore: (sqInt) squeakSem protocolNSString: (NSString *) nameString target: aTarget
 
60
{
 
61
        sem = squeakSem;
 
62
        if (nameString)
 
63
                protocol = objc_getProtocol([nameString UTF8String]);
 
64
        else
 
65
                protocol = nil;
 
66
        
 
67
        if (aTarget) {
 
68
                [self setTarget: aTarget];
 
69
        } else {
 
70
                NSObject *dummy = [[NSObject alloc] init];
 
71
                [self setTarget: dummy];
 
72
                [dummy release];
 
73
        }
 
74
        
 
75
        lockForSqueak = [[NSConditionLock alloc] initWithCondition: 0];
 
76
        sigs = [[NSMutableDictionary alloc] initWithCapacity: 10];
 
77
        isCarbonVM = NO;
 
78
        callbackid = 0;
 
79
        
 
80
        return self;
 
81
}
 
82
 
 
83
#include <dlfcn.h>
 
84
- (void) forwardInvocation: (NSInvocation*) anInvocation
 
85
{
 
86
        NSDate *timeout;
 
87
        //      NSLog(@"forwardInvocation: %@", anInvocation);
 
88
        //      NSLog(@"currentThread: %@", [NSThread currentThread]);
 
89
        SEL selector = [anInvocation selector];
 
90
        NSString *selectorString = NSStringFromSelector(selector);
 
91
        if (![sigs objectForKey: selectorString]) {
 
92
                [anInvocation invokeWithTarget: target];
 
93
                return;
 
94
        }
 
95
        
 
96
        if([lockForSqueak lockWhenCondition: 0 beforeDate: (timeout = [[NSDate alloc] initWithTimeIntervalSinceNow: 3.0])])
 
97
        { 
 
98
                // NSLog(@"inside lock 0");
 
99
                [lockForSqueak unlockWithCondition: 1];
 
100
                [timeout release];
 
101
                invocation = [anInvocation retain];
 
102
                
 
103
                // NSLog(@"signalling squeak");
 
104
                interpreterProxy->signalSemaphoreWithIndex(sem);
 
105
                
 
106
                if (isCarbonVM)
 
107
                        interpreterProxy->callbackEnter(&callbackid);
 
108
                
 
109
                if([lockForSqueak lockWhenCondition: 2 beforeDate: (timeout = [[NSDate alloc] initWithTimeIntervalSinceNow: 5.0])])
 
110
                {
 
111
                        // NSLog(@"inside lock 2");
 
112
                        [timeout release];
 
113
                        [invocation release];
 
114
                        invocation = nil;
 
115
                        [lockForSqueak unlockWithCondition: 0];
 
116
                }
 
117
                else
 
118
                {
 
119
                        // NSLog(@"failed lock 2");
 
120
                        [timeout release];
 
121
                        [invocation release];
 
122
                        invocation = nil;
 
123
                        [lockForSqueak unlockWithCondition: 0];
 
124
                }
 
125
                //NSLog(@"returning");
 
126
        }
 
127
        else
 
128
        {
 
129
                [timeout release];
 
130
                //NSLog(@"failed lock 0");
 
131
        }
 
132
}
 
133
 
 
134
- (NSMethodSignature *) methodSignatureForSelector: (SEL) selector
 
135
{
 
136
        NSMethodSignature* sig;
 
137
        NSString* sigAsString;
 
138
        sig = [target methodSignatureForSelector: selector];
 
139
        if (sig)
 
140
                return sig;
 
141
        
 
142
        sig = [super methodSignatureForSelector: selector];
 
143
        if(sig) 
 
144
                return sig;
 
145
        
 
146
        NSString *selectorString = NSStringFromSelector (selector);
 
147
        
 
148
        if (sigAsString = [sigs objectForKey: selectorString]) {
 
149
                
 
150
                if (protocol) {
 
151
                        struct objc_method_description methodDescription;
 
152
                        methodDescription = protocol_getMethodDescription(protocol, selector, YES, YES);
 
153
                        if(methodDescription.name == NULL) {
 
154
                                methodDescription = protocol_getMethodDescription(protocol, selector, NO, YES);
 
155
                        }
 
156
                        
 
157
                        if(methodDescription.name != NULL) {
 
158
                                NSMethodSignature *foo = [NSMethodSignature signatureWithObjCTypes:methodDescription.types];
 
159
                                return foo;
 
160
                        }
 
161
                }
 
162
                NSMethodSignature *foo = [NSMethodSignature signatureWithObjCTypes: [sigAsString cStringUsingEncoding: NSASCIIStringEncoding]];
 
163
                return foo;
 
164
        }
 
165
        
 
166
        return nil;
 
167
}       
 
168
 
 
169
- (BOOL) respondsToSelector: (SEL) selector
 
170
{
 
171
        if([super respondsToSelector: selector]) 
 
172
                return true;
 
173
        
 
174
        if ([target respondsToSelector: selector]) 
 
175
                return true;
 
176
        
 
177
        NSString *which = NSStringFromSelector(selector);
 
178
        
 
179
        if ([sigs objectForKey: which]) 
 
180
                return true;
 
181
        
 
182
        return false;
 
183
}
 
184
 
 
185
- (void) setReturnValue: (void*) pointer {
 
186
        [invocation setReturnValue: &pointer];
 
187
}
 
188
 
 
189
- (BOOL) isDataTypeAware {
 
190
        return YES;
 
191
}
 
192
 
 
193
- (void) setIsCarbonVM {
 
194
        isCarbonVM = YES;
 
195
}
 
196
 
 
197
- (void) dealloc
 
198
{
 
199
        [lockForSqueak release];
 
200
        [sigs release];
 
201
        [target release];
 
202
        [super dealloc];
 
203
}
 
204
 
 
205
@end
 
206