3 // Part of ASIHTTPRequest -> http://allseeing-i.com/ASIHTTPRequest
5 // Created by Ben Copsey on 10/08/2009.
6 // Copyright 2009 All-Seeing Interactive. All rights reserved.
9 #import "ASIInputStream.h"
10 #import "ASIHTTPRequest.h"
12 // Used to ensure only one request can read data at once
13 static NSLock *readLock = nil;
15 @implementation ASIInputStream
19 if (self == [ASIInputStream class]) {
20 readLock = [[NSLock alloc] init];
24 + (id)inputStreamWithFileAtPath:(NSString *)path request:(ASIHTTPRequest *)theRequest
26 ASIInputStream *theStream = [[[self alloc] init] autorelease];
27 [theStream setRequest:theRequest];
28 [theStream setStream:[NSInputStream inputStreamWithFileAtPath:path]];
32 + (id)inputStreamWithData:(NSData *)data request:(ASIHTTPRequest *)theRequest
34 ASIInputStream *theStream = [[[self alloc] init] autorelease];
35 [theStream setRequest:theRequest];
36 [theStream setStream:[NSInputStream inputStreamWithData:data]];
46 // Called when CFNetwork wants to read more of our request body
47 // When throttling is on, we ask ASIHTTPRequest for the maximum amount of data we can read
48 - (NSInteger)read:(uint8_t *)buffer maxLength:(NSUInteger)len
51 unsigned long toRead = len;
52 if ([ASIHTTPRequest isBandwidthThrottled]) {
53 toRead = [ASIHTTPRequest maxUploadReadLength];
56 } else if (toRead == 0) {
59 [request performThrottling];
61 [ASIHTTPRequest incrementBandwidthUsedInLastSecond:toRead];
63 return [stream read:buffer maxLength:toRead];
67 * Implement NSInputStream mandatory methods to make sure they are implemented
68 * (necessary for MacRuby for example) and avoid the overhead of method
69 * forwarding for these common methods.
83 return [stream delegate];
86 - (void)setDelegate:(id)delegate
88 [stream setDelegate:delegate];
91 - (void)scheduleInRunLoop:(NSRunLoop *)aRunLoop forMode:(NSString *)mode
93 [stream scheduleInRunLoop:aRunLoop forMode:mode];
96 - (void)removeFromRunLoop:(NSRunLoop *)aRunLoop forMode:(NSString *)mode
98 [stream removeFromRunLoop:aRunLoop forMode:mode];
101 - (id)propertyForKey:(NSString *)key
103 return [stream propertyForKey:key];
106 - (BOOL)setProperty:(id)property forKey:(NSString *)key
108 return [stream setProperty:property forKey:key];
111 - (NSStreamStatus)streamStatus
113 return [stream streamStatus];
116 - (NSError *)streamError
118 return [stream streamError];
121 // If we get asked to perform a method we don't have (probably internal ones),
122 // we'll just forward the message to our stream
124 - (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector
126 return [stream methodSignatureForSelector:aSelector];
129 - (void)forwardInvocation:(NSInvocation *)anInvocation
131 [anInvocation invokeWithTarget:stream];