Можно ли безопасно прочитать списки из ненадежного источника?

StackOverflow https://stackoverflow.com/questions/926956

  •  06-09-2019
  •  | 
  •  

Вопрос

Мне нужна простая связь клиент-сервер с приложением iPhone, и списки свойств XML кажутся довольно простым решением, которое избавляет меня от необходимости иметь дело с делегатами синтаксического анализатора XML и создавать эти структуры самостоятельно.

Мне просто интересно, разумно ли использовать класс NSPropertyListSerialization с внешними данными?Есть ли какие-либо неясные функции plist, которые можно было бы использовать?

Это было полезно?

Решение

Да, безопасно использовать NSPropertyListSerialization с ненадежными данными, но после того, как вы превратите пакет байтов в иерархию типов plist, вы должны проверить эти типы, чтобы убедиться, что они соответствуют вашему ожидаемому формату данных.

Например, если вы ожидаете получить словарь со строковыми ключами и NSNumbers в качестве значений, вы должны подтвердить это чем-то вроде:

NSString *errorDescription = nil;
NSPropertyListFormat format = 0;
id topObject = [NSPropertyListSerialization propertyListFromData:plistData mutabilityOption:NSPropertyListImmutable format:&format errorDescription:&errorDescription];
NSDictionary *validDictionary = nil;
if ([topObject isKindOfClass:[NSDictionary class]]) {
    BOOL allNumbers = YES;
    for(id value in [topObject allValues]) {
        allNumbers = allNumbers && [value isKindOfClass:[NSNumber class]];
    }
    if (allNumbers) {
        validDictionary = topObject;
    }
}
return validDictionary;

Если вы этого не сделаете, источник данных мог поместить в архив значения plist с неправильно подобранными типами или недопустимые значения, которые могли привести к неправильному поведению вашего клиента и в конечном итоге стать уязвимостью системы безопасности.

Другие советы

@Джон Хесс:Спасибо.Я создал NSDictionary категория, позволяющая сократить необходимое количество isKindOfClasses.

@interface NSDictionary (TypedDictionary)

-(NSArray *)arrayForKey:(NSString*)key;
-(NSString *)stringForKey:(NSString*)key;
-(NSDictionary *)dictionaryForKey:(NSString*)key;

@end


@implementation NSDictionary (TypedDictionary)

-(NSArray *)arrayForKey:(NSString*)key {
    NSArray *obj = [self objectForKey:key];
    return [obj isKindOfClass:[NSArray class]] ? obj : nil;
}
-(NSString *)stringForKey:(NSString*)key {
    NSString *obj = [self objectForKey:key];
    return [obj isKindOfClass:[NSString class]] ? obj : nil;
}
-(NSDictionary *)dictionaryForKey:(NSString*)key {
    NSDictionary *obj = [self objectForKey:key];
    return [obj isKindOfClass:[NSDictionary class]] ? obj : nil;
}
@end
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top