Skip to content

Instantly share code, notes, and snippets.

@rixth
Created July 22, 2012 02:57
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save rixth/3158063 to your computer and use it in GitHub Desktop.
Save rixth/3158063 to your computer and use it in GitHub Desktop.
A very naive bencoding decoder I wrote for a personal project.
//
// Bencoding.h
// bencoder
//
// Created by Thomas Rix on 7/21/12.
// Copyright (c) 2012 Thomas Rix. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Bencoding : NSObject
- (id)initWithString:(NSString *)str;
- (void)resetWithString:(NSString *)str;
- (id)decode;
@end
//
// Bencoding.m
// bencoder
//
// Created by Thomas Rix on 7/21/12.
// Copyright (c) 2012 Thomas Rix. All rights reserved.
//
#import "Bencoding.h"
@interface Bencoding ()
- (NSString *)decodeStr;
- (NSNumber *)decodeInt;
- (NSArray *)decodeList;
- (NSDictionary *)decodeDict;
- (NSString *)currentString;
@end
@implementation Bencoding {
NSString* _str;
int64_t _offset;
}
- (id)initWithString:(NSString *)str {
self = [super init];
if (self) {
[self resetWithString:str];
}
return self;
}
- (void)resetWithString:(NSString *)str {
_str = str;
_offset = 0;
}
- (id)decode {
switch ([[self currentString] characterAtIndex:0]) {
case 'i':
return [self decodeInt];
case 'l':
return [self decodeList];
case 'd':
return [self decodeDict];
default:
return [self decodeStr];
}
}
- (NSString *)decodeStr {
NSString* string = [self currentString];
NSInteger colonLocation = [string rangeOfString:@":"].location;
NSString* lengthString = [string substringWithRange:NSMakeRange(0, colonLocation)];
_offset += ([lengthString intValue] + colonLocation + 1);
return [string substringWithRange:NSMakeRange(colonLocation + 1, [lengthString intValue])];
}
- (NSNumber *)decodeInt {
NSString* intString = @"";
_offset++;
while ([[self currentString] characterAtIndex:0] != 'e') {
intString = [intString stringByAppendingFormat:@"%C", [[self currentString] characterAtIndex:0]];
_offset++;
}
_offset++;
return [NSNumber numberWithInt:[intString intValue]];
}
- (NSArray *)decodeList {
NSMutableArray* list = [[NSMutableArray alloc] init];
_offset++;
while ([[self currentString] characterAtIndex:0] != 'e') {
[list addObject:[self decode]];
}
_offset++;
return [NSArray arrayWithArray:list];
}
- (NSArray *)decodeDict {
NSMutableDictionary* dict = [[NSMutableDictionary alloc] init];
_offset++;
while ([[self currentString] characterAtIndex:0] != 'e') {
NSString* key = [self decode];
[dict setObject:[self decode] forKey:key];
}
_offset++;
return [NSDictionary dictionaryWithDictionary:dict];
}
- (NSString *)currentString {
return [_str substringFromIndex:_offset];
}
@end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment