Adjust to ObjFW changes
This commit is contained in:
parent
5059b34193
commit
15c922cdad
3 changed files with 66 additions and 166 deletions
|
@ -29,6 +29,8 @@
|
||||||
|
|
||||||
OF_ASSUME_NONNULL_BEGIN
|
OF_ASSUME_NONNULL_BEGIN
|
||||||
|
|
||||||
|
#define XMPP_CONNECTION_BUFFER_LENGTH 512
|
||||||
|
|
||||||
@class XMPPConnection;
|
@class XMPPConnection;
|
||||||
@class XMPPJID;
|
@class XMPPJID;
|
||||||
@class XMPPIQ;
|
@class XMPPIQ;
|
||||||
|
@ -110,8 +112,10 @@ OF_ASSUME_NONNULL_BEGIN
|
||||||
* @brief This callback is called when the connection was closed.
|
* @brief This callback is called when the connection was closed.
|
||||||
*
|
*
|
||||||
* @param connection The connection that was closed
|
* @param connection The connection that was closed
|
||||||
|
* @param error The error XML element the stream encountered or nil
|
||||||
*/
|
*/
|
||||||
- (void)connectionWasClosed: (XMPPConnection *)connection;
|
- (void)connectionWasClosed: (XMPPConnection *)connection
|
||||||
|
error: (nullable OFXMLElement *)error;
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* @brief This callback is called when the connection threw an exception.
|
* @brief This callback is called when the connection threw an exception.
|
||||||
|
@ -141,10 +145,10 @@ OF_ASSUME_NONNULL_BEGIN
|
||||||
/*!
|
/*!
|
||||||
* @brief A class which abstracts a connection to an XMPP service.
|
* @brief A class which abstracts a connection to an XMPP service.
|
||||||
*/
|
*/
|
||||||
@interface XMPPConnection: OFObject <OFXMLParserDelegate,
|
@interface XMPPConnection: OFObject
|
||||||
OFXMLElementBuilderDelegate>
|
|
||||||
{
|
{
|
||||||
OF_KINDOF(OFTCPSocket *) _socket;
|
OF_KINDOF(OFTCPSocket *) _socket;
|
||||||
|
char _buffer[XMPP_CONNECTION_BUFFER_LENGTH];
|
||||||
OFXMLParser *_parser, *_oldParser;
|
OFXMLParser *_parser, *_oldParser;
|
||||||
OFXMLElementBuilder *_elementBuilder, *_oldElementBuilder;
|
OFXMLElementBuilder *_elementBuilder, *_oldElementBuilder;
|
||||||
OFString *_Nullable _username, *_Nullable _password, *_Nullable _server;
|
OFString *_Nullable _username, *_Nullable _password, *_Nullable _server;
|
||||||
|
@ -157,6 +161,7 @@ OF_ASSUME_NONNULL_BEGIN
|
||||||
uint16_t _port;
|
uint16_t _port;
|
||||||
id <XMPPStorage> _Nullable _dataStorage;
|
id <XMPPStorage> _Nullable _dataStorage;
|
||||||
OFString *_Nullable _language;
|
OFString *_Nullable _language;
|
||||||
|
OFMutableArray *_nextSRVRecords;
|
||||||
XMPPMulticastDelegate *_delegates;
|
XMPPMulticastDelegate *_delegates;
|
||||||
OFMutableDictionary OF_GENERIC(OFString *, XMPPCallback *) *_callbacks;
|
OFMutableDictionary OF_GENERIC(OFString *, XMPPCallback *) *_callbacks;
|
||||||
XMPPAuthenticator *_authModule;
|
XMPPAuthenticator *_authModule;
|
||||||
|
|
|
@ -56,26 +56,11 @@
|
||||||
|
|
||||||
#import <ObjFW/macros.h>
|
#import <ObjFW/macros.h>
|
||||||
|
|
||||||
#define BUFFER_LENGTH 512
|
@interface XMPPConnection () <OFDNSResolverDelegate, OFTCPSocketDelegate,
|
||||||
|
OFXMLParserDelegate, OFXMLElementBuilderDelegate>
|
||||||
@interface XMPPConnection ()
|
- (void)xmpp_tryNextSRVRecord;
|
||||||
- (void)xmpp_socketDidConnect: (OFTCPSocket *)socket
|
|
||||||
context: (OFArray *)nextSRVRecords
|
|
||||||
exception: (id)exception;
|
|
||||||
- (void)xmpp_tryNextSRVRecord: (OFArray *)SRVRecords;
|
|
||||||
- (void)xmpp_resolver: (OFDNSResolver *)resolver
|
|
||||||
didResolveDomainName: (OFString *)domainName
|
|
||||||
answerRecords: (OFDictionary *)answerRecords
|
|
||||||
authorityRecords: (OFDictionary *)authorityRecords
|
|
||||||
additionalRecords: (OFDictionary *)additionalRecords
|
|
||||||
context: (OFString *)domainToASCII
|
|
||||||
exception: (id)exception;
|
|
||||||
- (bool)xmpp_parseBuffer: (const void *)buffer
|
- (bool)xmpp_parseBuffer: (const void *)buffer
|
||||||
length: (size_t)length;
|
length: (size_t)length;
|
||||||
- (bool)xmpp_stream: (OFStream *)stream
|
|
||||||
didReadIntoBuffer: (char *)buffer
|
|
||||||
length: (size_t)length
|
|
||||||
exception: (OFException *)exception;
|
|
||||||
- (void)xmpp_startStream;
|
- (void)xmpp_startStream;
|
||||||
- (void)xmpp_handleStanza: (OFXMLElement *)element;
|
- (void)xmpp_handleStanza: (OFXMLElement *)element;
|
||||||
- (void)xmpp_handleStream: (OFXMLElement *)element;
|
- (void)xmpp_handleStream: (OFXMLElement *)element;
|
||||||
|
@ -142,6 +127,7 @@
|
||||||
[_domain release];
|
[_domain release];
|
||||||
[_resource release];
|
[_resource release];
|
||||||
[_JID release];
|
[_JID release];
|
||||||
|
[_nextSRVRecords release];
|
||||||
[_delegates release];
|
[_delegates release];
|
||||||
[_callbacks release];
|
[_callbacks release];
|
||||||
[_authModule release];
|
[_authModule release];
|
||||||
|
@ -271,20 +257,19 @@
|
||||||
[old release];
|
[old release];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)xmpp_socketDidConnect: (OFTCPSocket *)socket
|
- (void)socket: (OF_KINDOF(OFTCPSocket *))sock
|
||||||
context: (OFArray *)nextSRVRecords
|
didConnectToHost: (OFString *)host
|
||||||
|
port: (uint16_t)port
|
||||||
exception: (id)exception
|
exception: (id)exception
|
||||||
{
|
{
|
||||||
char *buffer;
|
|
||||||
|
|
||||||
if (exception != nil) {
|
if (exception != nil) {
|
||||||
if (nextSRVRecords != nil) {
|
if ([_nextSRVRecords count] > 0) {
|
||||||
[self xmpp_tryNextSRVRecord: nextSRVRecords];
|
[self xmpp_tryNextSRVRecord];
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
[_delegates
|
[_delegates broadcastSelector: @selector(connection:
|
||||||
broadcastSelector: @selector(connection:didThrowException:)
|
didThrowException:)
|
||||||
withObject: self
|
withObject: self
|
||||||
withObject: exception];
|
withObject: exception];
|
||||||
return;
|
return;
|
||||||
|
@ -292,38 +277,29 @@
|
||||||
|
|
||||||
[self xmpp_startStream];
|
[self xmpp_startStream];
|
||||||
|
|
||||||
buffer = [self allocMemoryWithSize: BUFFER_LENGTH];
|
[_socket asyncReadIntoBuffer: _buffer
|
||||||
[_socket asyncReadIntoBuffer: buffer
|
length: XMPP_CONNECTION_BUFFER_LENGTH];
|
||||||
length: BUFFER_LENGTH
|
|
||||||
target: self
|
|
||||||
selector: @selector(xmpp_stream:didReadIntoBuffer:
|
|
||||||
length:exception:)
|
|
||||||
context: nil];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)xmpp_tryNextSRVRecord: (OFArray *)SRVRecords
|
- (void)xmpp_tryNextSRVRecord
|
||||||
{
|
{
|
||||||
OFSRVDNSResourceRecord *record = [SRVRecords objectAtIndex: 0];
|
OFSRVDNSResourceRecord *record =
|
||||||
|
[[[_nextSRVRecords objectAtIndex: 0] copy] autorelease];
|
||||||
|
|
||||||
SRVRecords = [SRVRecords objectsInRange:
|
if ([_nextSRVRecords count] == 0) {
|
||||||
of_range(1, [SRVRecords count] - 1)];
|
[_nextSRVRecords release];
|
||||||
if ([SRVRecords count] == 0)
|
_nextSRVRecords = nil;
|
||||||
SRVRecords = nil;
|
}
|
||||||
|
|
||||||
[_socket asyncConnectToHost: [record target]
|
[_socket asyncConnectToHost: [record target]
|
||||||
port: [record port]
|
port: [record port]];
|
||||||
target: self
|
|
||||||
selector: @selector(xmpp_socketDidConnect:
|
|
||||||
context:exception:)
|
|
||||||
context: SRVRecords];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)xmpp_resolver: (OFDNSResolver *)resolver
|
- (void)resolver: (OFDNSResolver *)resolver
|
||||||
didResolveDomainName: (OFString *)domainName
|
didResolveDomainName: (OFString *)domainName
|
||||||
answerRecords: (OFDictionary *)answerRecords
|
answerRecords: (OFDictionary *)answerRecords
|
||||||
authorityRecords: (OFDictionary *)authorityRecords
|
authorityRecords: (OFDictionary *)authorityRecords
|
||||||
additionalRecords: (OFDictionary *)additionalRecords
|
additionalRecords: (OFDictionary *)additionalRecords
|
||||||
context: (OFString *)domainToASCII
|
|
||||||
exception: (id)exception
|
exception: (id)exception
|
||||||
{
|
{
|
||||||
OFMutableArray *records = [OFMutableArray array];
|
OFMutableArray *records = [OFMutableArray array];
|
||||||
|
@ -345,17 +321,16 @@
|
||||||
[records makeImmutable];
|
[records makeImmutable];
|
||||||
|
|
||||||
if ([records count] == 0) {
|
if ([records count] == 0) {
|
||||||
/* Fall back to A / AAA record. */
|
/* Fall back to A / AAAA record. */
|
||||||
[_socket asyncConnectToHost: domainToASCII
|
[_socket asyncConnectToHost: _domainToASCII
|
||||||
port: _port
|
port: _port];
|
||||||
target: self
|
|
||||||
selector: @selector(xmpp_socketDidConnect:
|
|
||||||
context:exception:)
|
|
||||||
context: nil];
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
[self xmpp_tryNextSRVRecord: records];
|
[_nextSRVRecords release];
|
||||||
|
_nextSRVRecords = nil;
|
||||||
|
_nextSRVRecords = [records mutableCopy];
|
||||||
|
[self xmpp_tryNextSRVRecord];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)asyncConnect
|
- (void)asyncConnect
|
||||||
|
@ -366,23 +341,14 @@
|
||||||
@throw [OFAlreadyConnectedException exception];
|
@throw [OFAlreadyConnectedException exception];
|
||||||
|
|
||||||
_socket = [[OFTCPSocket alloc] init];
|
_socket = [[OFTCPSocket alloc] init];
|
||||||
|
[_socket setDelegate: self];
|
||||||
|
|
||||||
if (_server != nil)
|
if (_server != nil)
|
||||||
[_socket asyncConnectToHost: _server
|
[_socket asyncConnectToHost: _server
|
||||||
port: _port
|
port: _port];
|
||||||
target: self
|
|
||||||
selector: @selector(xmpp_socketDidConnect:
|
|
||||||
context:exception:)
|
|
||||||
context: nil];
|
|
||||||
else
|
else
|
||||||
[[OFThread DNSResolver]
|
[[OFThread DNSResolver] asyncResolveHost: _domainToASCII
|
||||||
asyncResolveHost: _domainToASCII
|
delegate: self];
|
||||||
target: self
|
|
||||||
selector: @selector(xmpp_resolver:
|
|
||||||
didResolveDomainName:answerRecords:
|
|
||||||
authorityRecords:additionalRecords:
|
|
||||||
context:exception:)
|
|
||||||
context: _domainToASCII];
|
|
||||||
|
|
||||||
objc_autoreleasePoolPop(pool);
|
objc_autoreleasePoolPop(pool);
|
||||||
}
|
}
|
||||||
|
@ -391,8 +357,10 @@
|
||||||
length: (size_t)length
|
length: (size_t)length
|
||||||
{
|
{
|
||||||
if ([_socket isAtEndOfStream]) {
|
if ([_socket isAtEndOfStream]) {
|
||||||
[_delegates broadcastSelector: @selector(connectionWasClosed:)
|
[_delegates broadcastSelector: @selector(connectionWasClosed:
|
||||||
withObject: self];
|
error:)
|
||||||
|
withObject: self
|
||||||
|
withObject: nil];
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -422,10 +390,10 @@
|
||||||
_oldElementBuilder = nil;
|
_oldElementBuilder = nil;
|
||||||
}
|
}
|
||||||
|
|
||||||
- (bool)xmpp_stream: (OFStream *)stream
|
- (bool)stream: (OF_KINDOF(OFStream *))stream
|
||||||
didReadIntoBuffer: (char *)buffer
|
didReadIntoBuffer: (void *)buffer
|
||||||
length: (size_t)length
|
length: (size_t)length
|
||||||
exception: (OFException *)exception
|
exception: (id)exception
|
||||||
{
|
{
|
||||||
if (exception != nil) {
|
if (exception != nil) {
|
||||||
[_delegates broadcastSelector: @selector(connection:
|
[_delegates broadcastSelector: @selector(connection:
|
||||||
|
@ -456,14 +424,8 @@
|
||||||
_oldParser = nil;
|
_oldParser = nil;
|
||||||
_oldElementBuilder = nil;
|
_oldElementBuilder = nil;
|
||||||
|
|
||||||
[_socket asyncReadIntoBuffer: buffer
|
[_socket asyncReadIntoBuffer: _buffer
|
||||||
length: BUFFER_LENGTH
|
length: XMPP_CONNECTION_BUFFER_LENGTH];
|
||||||
target: self
|
|
||||||
selector: @selector(xmpp_stream:
|
|
||||||
didReadIntoBuffer:length:
|
|
||||||
exception:)
|
|
||||||
context: nil];
|
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -586,7 +548,7 @@
|
||||||
- (void)parser: (OFXMLParser *)parser
|
- (void)parser: (OFXMLParser *)parser
|
||||||
didStartElement: (OFString *)name
|
didStartElement: (OFString *)name
|
||||||
prefix: (OFString *)prefix
|
prefix: (OFString *)prefix
|
||||||
namespace: (OFString *)NS
|
namespace: (OFString *)namespace
|
||||||
attributes: (OFArray *)attributes
|
attributes: (OFArray *)attributes
|
||||||
{
|
{
|
||||||
if (![name isEqual: @"stream"]) {
|
if (![name isEqual: @"stream"]) {
|
||||||
|
@ -602,7 +564,7 @@
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (![NS isEqual: XMPP_NS_STREAM]) {
|
if (![namespace isEqual: XMPP_NS_STREAM]) {
|
||||||
[self xmpp_sendStreamError: @"invalid-namespace"
|
[self xmpp_sendStreamError: @"invalid-namespace"
|
||||||
text: nil];
|
text: nil];
|
||||||
return;
|
return;
|
||||||
|
@ -755,84 +717,15 @@
|
||||||
if ([[element name] isEqual: @"error"]) {
|
if ([[element name] isEqual: @"error"]) {
|
||||||
OFString *condition, *reason;
|
OFString *condition, *reason;
|
||||||
[self close];
|
[self close];
|
||||||
[_socket close]; // Remote has already closed his stream
|
|
||||||
|
|
||||||
if ([element elementForName: @"bad-format"
|
[_delegates broadcastSelector: @selector(connectionWasClosed:)
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
withObject: self
|
||||||
condition = @"bad-format";
|
withObject: element];
|
||||||
else if ([element elementForName: @"bad-namespace-prefix"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
condition = [[[element elementsForNamespace:
|
||||||
condition = @"bad-namespace-prefix";
|
XMPP_NS_XMPP_STREAM] firstObject] name];
|
||||||
else if ([element elementForName: @"conflict"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
if (condition == nil)
|
||||||
condition = @"conflict";
|
|
||||||
else if ([element elementForName: @"connection-timeout"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"connection-timeout";
|
|
||||||
else if ([element elementForName: @"host-gone"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"host-gone";
|
|
||||||
else if ([element elementForName: @"host-unknown"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"host-unknown";
|
|
||||||
else if ([element elementForName: @"improper-addressing"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"improper-addressing";
|
|
||||||
else if ([element elementForName: @"internal-server-error"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"internal-server-error";
|
|
||||||
else if ([element elementForName: @"invalid-from"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"invalid-from";
|
|
||||||
else if ([element elementForName: @"invalid-namespace"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"invalid-namespace";
|
|
||||||
else if ([element elementForName: @"invalid-xml"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"invalid-xml";
|
|
||||||
else if ([element elementForName: @"not-authorized"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"not-authorized";
|
|
||||||
else if ([element elementForName: @"not-well-formed"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"not-well-formed";
|
|
||||||
else if ([element elementForName: @"policy-violation"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"policy-violation";
|
|
||||||
else if ([element elementForName: @"remote-connection-failed"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"remote-connection-failed";
|
|
||||||
else if ([element elementForName: @"reset"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"reset";
|
|
||||||
else if ([element elementForName: @"resource-constraint"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"resource-constraint";
|
|
||||||
else if ([element elementForName: @"restricted-xml"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"restricted-xml";
|
|
||||||
else if ([element elementForName: @"see-other-host"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"see-other-host";
|
|
||||||
else if ([element elementForName: @"system-shutdown"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"system-shutdown";
|
|
||||||
else if ([element elementForName: @"undefined-condition"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"undefined-condition";
|
|
||||||
else if ([element elementForName: @"unsupported-encoding"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"unsupported-encoding";
|
|
||||||
else if ([element elementForName: @"unsupported-feature"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"unsupported-feature";
|
|
||||||
else if ([element elementForName: @"unsupported-stanza-type"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"unsupported-stanza-type";
|
|
||||||
else if ([element elementForName: @"unsupported-version"
|
|
||||||
namespace: XMPP_NS_XMPP_STREAM])
|
|
||||||
condition = @"unsupported-version";
|
|
||||||
else
|
|
||||||
condition = @"undefined";
|
condition = @"undefined";
|
||||||
|
|
||||||
reason = [[element
|
reason = [[element
|
||||||
|
@ -870,6 +763,7 @@
|
||||||
[newSock startTLSWithExpectedHost: nil];
|
[newSock startTLSWithExpectedHost: nil];
|
||||||
[_socket release];
|
[_socket release];
|
||||||
_socket = newSock;
|
_socket = newSock;
|
||||||
|
[_socket setDelegate: self];
|
||||||
|
|
||||||
_encrypted = true;
|
_encrypted = true;
|
||||||
|
|
||||||
|
|
|
@ -269,7 +269,8 @@ OF_APPLICATION_DELEGATE(AppDelegate)
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)connectionWasClosed: (XMPPConnection *)conn
|
- (void)connectionWasClosed: (XMPPConnection *)conn
|
||||||
|
error: (OFXMLElement *)error
|
||||||
{
|
{
|
||||||
of_log(@"Connection was closed!");
|
of_log(@"Connection was closed: %@", error);
|
||||||
}
|
}
|
||||||
@end
|
@end
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue