GPBMessage.m 126 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366
  1. // Protocol Buffers - Google's data interchange format
  2. // Copyright 2008 Google Inc. All rights reserved.
  3. // https://developers.google.com/protocol-buffers/
  4. //
  5. // Redistribution and use in source and binary forms, with or without
  6. // modification, are permitted provided that the following conditions are
  7. // met:
  8. //
  9. // * Redistributions of source code must retain the above copyright
  10. // notice, this list of conditions and the following disclaimer.
  11. // * Redistributions in binary form must reproduce the above
  12. // copyright notice, this list of conditions and the following disclaimer
  13. // in the documentation and/or other materials provided with the
  14. // distribution.
  15. // * Neither the name of Google Inc. nor the names of its
  16. // contributors may be used to endorse or promote products derived from
  17. // this software without specific prior written permission.
  18. //
  19. // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  20. // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  21. // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  22. // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
  23. // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  24. // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
  25. // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  26. // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  27. // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  28. // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  29. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  30. #import "GPBMessage_PackagePrivate.h"
  31. #import <objc/runtime.h>
  32. #import <objc/message.h>
  33. #import <stdatomic.h>
  34. #import "GPBArray_PackagePrivate.h"
  35. #import "GPBCodedInputStream_PackagePrivate.h"
  36. #import "GPBCodedOutputStream_PackagePrivate.h"
  37. #import "GPBDescriptor_PackagePrivate.h"
  38. #import "GPBDictionary_PackagePrivate.h"
  39. #import "GPBExtensionInternals.h"
  40. #import "GPBExtensionRegistry.h"
  41. #import "GPBRootObject_PackagePrivate.h"
  42. #import "GPBUnknownFieldSet_PackagePrivate.h"
  43. #import "GPBUtilities_PackagePrivate.h"
  44. // Direct access is use for speed, to avoid even internally declaring things
  45. // read/write, etc. The warning is enabled in the project to ensure code calling
  46. // protos can turn on -Wdirect-ivar-access without issues.
  47. #pragma clang diagnostic push
  48. #pragma clang diagnostic ignored "-Wdirect-ivar-access"
  49. NSString *const GPBMessageErrorDomain =
  50. GPBNSStringifySymbol(GPBMessageErrorDomain);
  51. NSString *const GPBErrorReasonKey = @"Reason";
  52. static NSString *const kGPBDataCoderKey = @"GPBData";
  53. //
  54. // PLEASE REMEMBER:
  55. //
  56. // This is the base class for *all* messages generated, so any selector defined,
  57. // *public* or *private* could end up colliding with a proto message field. So
  58. // avoid using selectors that could match a property, use C functions to hide
  59. // them, etc.
  60. //
  61. @interface GPBMessage () {
  62. @package
  63. GPBUnknownFieldSet *unknownFields_;
  64. NSMutableDictionary *extensionMap_;
  65. NSMutableDictionary *autocreatedExtensionMap_;
  66. // If the object was autocreated, we remember the creator so that if we get
  67. // mutated, we can inform the creator to make our field visible.
  68. GPBMessage *autocreator_;
  69. GPBFieldDescriptor *autocreatorField_;
  70. GPBExtensionDescriptor *autocreatorExtension_;
  71. // A lock to provide mutual exclusion from internal data that can be modified
  72. // by *read* operations such as getters (autocreation of message fields and
  73. // message extensions, not setting of values). Used to guarantee thread safety
  74. // for concurrent reads on the message.
  75. // NOTE: OSSpinLock may seem like a good fit here but Apple engineers have
  76. // pointed out that they are vulnerable to live locking on iOS in cases of
  77. // priority inversion:
  78. // http://mjtsai.com/blog/2015/12/16/osspinlock-is-unsafe/
  79. // https://lists.swift.org/pipermail/swift-dev/Week-of-Mon-20151214/000372.html
  80. // Use of readOnlySemaphore_ must be prefaced by a call to
  81. // GPBPrepareReadOnlySemaphore to ensure it has been created. This allows
  82. // readOnlySemaphore_ to be only created when actually needed.
  83. _Atomic(dispatch_semaphore_t) readOnlySemaphore_;
  84. }
  85. @end
  86. static id CreateArrayForField(GPBFieldDescriptor *field,
  87. GPBMessage *autocreator)
  88. __attribute__((ns_returns_retained));
  89. static id GetOrCreateArrayIvarWithField(GPBMessage *self,
  90. GPBFieldDescriptor *field);
  91. static id GetArrayIvarWithField(GPBMessage *self, GPBFieldDescriptor *field);
  92. static id CreateMapForField(GPBFieldDescriptor *field,
  93. GPBMessage *autocreator)
  94. __attribute__((ns_returns_retained));
  95. static id GetOrCreateMapIvarWithField(GPBMessage *self,
  96. GPBFieldDescriptor *field);
  97. static id GetMapIvarWithField(GPBMessage *self, GPBFieldDescriptor *field);
  98. static NSMutableDictionary *CloneExtensionMap(NSDictionary *extensionMap,
  99. NSZone *zone)
  100. __attribute__((ns_returns_retained));
  101. #ifdef DEBUG
  102. static NSError *MessageError(NSInteger code, NSDictionary *userInfo) {
  103. return [NSError errorWithDomain:GPBMessageErrorDomain
  104. code:code
  105. userInfo:userInfo];
  106. }
  107. #endif
  108. static NSError *ErrorFromException(NSException *exception) {
  109. NSError *error = nil;
  110. if ([exception.name isEqual:GPBCodedInputStreamException]) {
  111. NSDictionary *exceptionInfo = exception.userInfo;
  112. error = exceptionInfo[GPBCodedInputStreamUnderlyingErrorKey];
  113. }
  114. if (!error) {
  115. NSString *reason = exception.reason;
  116. NSDictionary *userInfo = nil;
  117. if ([reason length]) {
  118. userInfo = @{ GPBErrorReasonKey : reason };
  119. }
  120. error = [NSError errorWithDomain:GPBMessageErrorDomain
  121. code:GPBMessageErrorCodeOther
  122. userInfo:userInfo];
  123. }
  124. return error;
  125. }
  126. static void CheckExtension(GPBMessage *self,
  127. GPBExtensionDescriptor *extension) {
  128. if (![self isKindOfClass:extension.containingMessageClass]) {
  129. [NSException
  130. raise:NSInvalidArgumentException
  131. format:@"Extension %@ used on wrong class (%@ instead of %@)",
  132. extension.singletonName,
  133. [self class], extension.containingMessageClass];
  134. }
  135. }
  136. static NSMutableDictionary *CloneExtensionMap(NSDictionary *extensionMap,
  137. NSZone *zone) {
  138. if (extensionMap.count == 0) {
  139. return nil;
  140. }
  141. NSMutableDictionary *result = [[NSMutableDictionary allocWithZone:zone]
  142. initWithCapacity:extensionMap.count];
  143. for (GPBExtensionDescriptor *extension in extensionMap) {
  144. id value = [extensionMap objectForKey:extension];
  145. BOOL isMessageExtension = GPBExtensionIsMessage(extension);
  146. if (extension.repeated) {
  147. if (isMessageExtension) {
  148. NSMutableArray *list =
  149. [[NSMutableArray alloc] initWithCapacity:[value count]];
  150. for (GPBMessage *listValue in value) {
  151. GPBMessage *copiedValue = [listValue copyWithZone:zone];
  152. [list addObject:copiedValue];
  153. [copiedValue release];
  154. }
  155. [result setObject:list forKey:extension];
  156. [list release];
  157. } else {
  158. NSMutableArray *copiedValue = [value mutableCopyWithZone:zone];
  159. [result setObject:copiedValue forKey:extension];
  160. [copiedValue release];
  161. }
  162. } else {
  163. if (isMessageExtension) {
  164. GPBMessage *copiedValue = [value copyWithZone:zone];
  165. [result setObject:copiedValue forKey:extension];
  166. [copiedValue release];
  167. } else {
  168. [result setObject:value forKey:extension];
  169. }
  170. }
  171. }
  172. return result;
  173. }
  174. static id CreateArrayForField(GPBFieldDescriptor *field,
  175. GPBMessage *autocreator) {
  176. id result;
  177. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  178. switch (fieldDataType) {
  179. case GPBDataTypeBool:
  180. result = [[GPBBoolArray alloc] init];
  181. break;
  182. case GPBDataTypeFixed32:
  183. case GPBDataTypeUInt32:
  184. result = [[GPBUInt32Array alloc] init];
  185. break;
  186. case GPBDataTypeInt32:
  187. case GPBDataTypeSFixed32:
  188. case GPBDataTypeSInt32:
  189. result = [[GPBInt32Array alloc] init];
  190. break;
  191. case GPBDataTypeFixed64:
  192. case GPBDataTypeUInt64:
  193. result = [[GPBUInt64Array alloc] init];
  194. break;
  195. case GPBDataTypeInt64:
  196. case GPBDataTypeSFixed64:
  197. case GPBDataTypeSInt64:
  198. result = [[GPBInt64Array alloc] init];
  199. break;
  200. case GPBDataTypeFloat:
  201. result = [[GPBFloatArray alloc] init];
  202. break;
  203. case GPBDataTypeDouble:
  204. result = [[GPBDoubleArray alloc] init];
  205. break;
  206. case GPBDataTypeEnum:
  207. result = [[GPBEnumArray alloc]
  208. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  209. break;
  210. case GPBDataTypeBytes:
  211. case GPBDataTypeGroup:
  212. case GPBDataTypeMessage:
  213. case GPBDataTypeString:
  214. if (autocreator) {
  215. result = [[GPBAutocreatedArray alloc] init];
  216. } else {
  217. result = [[NSMutableArray alloc] init];
  218. }
  219. break;
  220. }
  221. if (autocreator) {
  222. if (GPBDataTypeIsObject(fieldDataType)) {
  223. GPBAutocreatedArray *autoArray = result;
  224. autoArray->_autocreator = autocreator;
  225. } else {
  226. GPBInt32Array *gpbArray = result;
  227. gpbArray->_autocreator = autocreator;
  228. }
  229. }
  230. return result;
  231. }
  232. static id CreateMapForField(GPBFieldDescriptor *field,
  233. GPBMessage *autocreator) {
  234. id result;
  235. GPBDataType keyDataType = field.mapKeyDataType;
  236. GPBDataType valueDataType = GPBGetFieldDataType(field);
  237. switch (keyDataType) {
  238. case GPBDataTypeBool:
  239. switch (valueDataType) {
  240. case GPBDataTypeBool:
  241. result = [[GPBBoolBoolDictionary alloc] init];
  242. break;
  243. case GPBDataTypeFixed32:
  244. case GPBDataTypeUInt32:
  245. result = [[GPBBoolUInt32Dictionary alloc] init];
  246. break;
  247. case GPBDataTypeInt32:
  248. case GPBDataTypeSFixed32:
  249. case GPBDataTypeSInt32:
  250. result = [[GPBBoolInt32Dictionary alloc] init];
  251. break;
  252. case GPBDataTypeFixed64:
  253. case GPBDataTypeUInt64:
  254. result = [[GPBBoolUInt64Dictionary alloc] init];
  255. break;
  256. case GPBDataTypeInt64:
  257. case GPBDataTypeSFixed64:
  258. case GPBDataTypeSInt64:
  259. result = [[GPBBoolInt64Dictionary alloc] init];
  260. break;
  261. case GPBDataTypeFloat:
  262. result = [[GPBBoolFloatDictionary alloc] init];
  263. break;
  264. case GPBDataTypeDouble:
  265. result = [[GPBBoolDoubleDictionary alloc] init];
  266. break;
  267. case GPBDataTypeEnum:
  268. result = [[GPBBoolEnumDictionary alloc]
  269. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  270. break;
  271. case GPBDataTypeBytes:
  272. case GPBDataTypeMessage:
  273. case GPBDataTypeString:
  274. result = [[GPBBoolObjectDictionary alloc] init];
  275. break;
  276. case GPBDataTypeGroup:
  277. NSCAssert(NO, @"shouldn't happen");
  278. return nil;
  279. }
  280. break;
  281. case GPBDataTypeFixed32:
  282. case GPBDataTypeUInt32:
  283. switch (valueDataType) {
  284. case GPBDataTypeBool:
  285. result = [[GPBUInt32BoolDictionary alloc] init];
  286. break;
  287. case GPBDataTypeFixed32:
  288. case GPBDataTypeUInt32:
  289. result = [[GPBUInt32UInt32Dictionary alloc] init];
  290. break;
  291. case GPBDataTypeInt32:
  292. case GPBDataTypeSFixed32:
  293. case GPBDataTypeSInt32:
  294. result = [[GPBUInt32Int32Dictionary alloc] init];
  295. break;
  296. case GPBDataTypeFixed64:
  297. case GPBDataTypeUInt64:
  298. result = [[GPBUInt32UInt64Dictionary alloc] init];
  299. break;
  300. case GPBDataTypeInt64:
  301. case GPBDataTypeSFixed64:
  302. case GPBDataTypeSInt64:
  303. result = [[GPBUInt32Int64Dictionary alloc] init];
  304. break;
  305. case GPBDataTypeFloat:
  306. result = [[GPBUInt32FloatDictionary alloc] init];
  307. break;
  308. case GPBDataTypeDouble:
  309. result = [[GPBUInt32DoubleDictionary alloc] init];
  310. break;
  311. case GPBDataTypeEnum:
  312. result = [[GPBUInt32EnumDictionary alloc]
  313. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  314. break;
  315. case GPBDataTypeBytes:
  316. case GPBDataTypeMessage:
  317. case GPBDataTypeString:
  318. result = [[GPBUInt32ObjectDictionary alloc] init];
  319. break;
  320. case GPBDataTypeGroup:
  321. NSCAssert(NO, @"shouldn't happen");
  322. return nil;
  323. }
  324. break;
  325. case GPBDataTypeInt32:
  326. case GPBDataTypeSFixed32:
  327. case GPBDataTypeSInt32:
  328. switch (valueDataType) {
  329. case GPBDataTypeBool:
  330. result = [[GPBInt32BoolDictionary alloc] init];
  331. break;
  332. case GPBDataTypeFixed32:
  333. case GPBDataTypeUInt32:
  334. result = [[GPBInt32UInt32Dictionary alloc] init];
  335. break;
  336. case GPBDataTypeInt32:
  337. case GPBDataTypeSFixed32:
  338. case GPBDataTypeSInt32:
  339. result = [[GPBInt32Int32Dictionary alloc] init];
  340. break;
  341. case GPBDataTypeFixed64:
  342. case GPBDataTypeUInt64:
  343. result = [[GPBInt32UInt64Dictionary alloc] init];
  344. break;
  345. case GPBDataTypeInt64:
  346. case GPBDataTypeSFixed64:
  347. case GPBDataTypeSInt64:
  348. result = [[GPBInt32Int64Dictionary alloc] init];
  349. break;
  350. case GPBDataTypeFloat:
  351. result = [[GPBInt32FloatDictionary alloc] init];
  352. break;
  353. case GPBDataTypeDouble:
  354. result = [[GPBInt32DoubleDictionary alloc] init];
  355. break;
  356. case GPBDataTypeEnum:
  357. result = [[GPBInt32EnumDictionary alloc]
  358. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  359. break;
  360. case GPBDataTypeBytes:
  361. case GPBDataTypeMessage:
  362. case GPBDataTypeString:
  363. result = [[GPBInt32ObjectDictionary alloc] init];
  364. break;
  365. case GPBDataTypeGroup:
  366. NSCAssert(NO, @"shouldn't happen");
  367. return nil;
  368. }
  369. break;
  370. case GPBDataTypeFixed64:
  371. case GPBDataTypeUInt64:
  372. switch (valueDataType) {
  373. case GPBDataTypeBool:
  374. result = [[GPBUInt64BoolDictionary alloc] init];
  375. break;
  376. case GPBDataTypeFixed32:
  377. case GPBDataTypeUInt32:
  378. result = [[GPBUInt64UInt32Dictionary alloc] init];
  379. break;
  380. case GPBDataTypeInt32:
  381. case GPBDataTypeSFixed32:
  382. case GPBDataTypeSInt32:
  383. result = [[GPBUInt64Int32Dictionary alloc] init];
  384. break;
  385. case GPBDataTypeFixed64:
  386. case GPBDataTypeUInt64:
  387. result = [[GPBUInt64UInt64Dictionary alloc] init];
  388. break;
  389. case GPBDataTypeInt64:
  390. case GPBDataTypeSFixed64:
  391. case GPBDataTypeSInt64:
  392. result = [[GPBUInt64Int64Dictionary alloc] init];
  393. break;
  394. case GPBDataTypeFloat:
  395. result = [[GPBUInt64FloatDictionary alloc] init];
  396. break;
  397. case GPBDataTypeDouble:
  398. result = [[GPBUInt64DoubleDictionary alloc] init];
  399. break;
  400. case GPBDataTypeEnum:
  401. result = [[GPBUInt64EnumDictionary alloc]
  402. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  403. break;
  404. case GPBDataTypeBytes:
  405. case GPBDataTypeMessage:
  406. case GPBDataTypeString:
  407. result = [[GPBUInt64ObjectDictionary alloc] init];
  408. break;
  409. case GPBDataTypeGroup:
  410. NSCAssert(NO, @"shouldn't happen");
  411. return nil;
  412. }
  413. break;
  414. case GPBDataTypeInt64:
  415. case GPBDataTypeSFixed64:
  416. case GPBDataTypeSInt64:
  417. switch (valueDataType) {
  418. case GPBDataTypeBool:
  419. result = [[GPBInt64BoolDictionary alloc] init];
  420. break;
  421. case GPBDataTypeFixed32:
  422. case GPBDataTypeUInt32:
  423. result = [[GPBInt64UInt32Dictionary alloc] init];
  424. break;
  425. case GPBDataTypeInt32:
  426. case GPBDataTypeSFixed32:
  427. case GPBDataTypeSInt32:
  428. result = [[GPBInt64Int32Dictionary alloc] init];
  429. break;
  430. case GPBDataTypeFixed64:
  431. case GPBDataTypeUInt64:
  432. result = [[GPBInt64UInt64Dictionary alloc] init];
  433. break;
  434. case GPBDataTypeInt64:
  435. case GPBDataTypeSFixed64:
  436. case GPBDataTypeSInt64:
  437. result = [[GPBInt64Int64Dictionary alloc] init];
  438. break;
  439. case GPBDataTypeFloat:
  440. result = [[GPBInt64FloatDictionary alloc] init];
  441. break;
  442. case GPBDataTypeDouble:
  443. result = [[GPBInt64DoubleDictionary alloc] init];
  444. break;
  445. case GPBDataTypeEnum:
  446. result = [[GPBInt64EnumDictionary alloc]
  447. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  448. break;
  449. case GPBDataTypeBytes:
  450. case GPBDataTypeMessage:
  451. case GPBDataTypeString:
  452. result = [[GPBInt64ObjectDictionary alloc] init];
  453. break;
  454. case GPBDataTypeGroup:
  455. NSCAssert(NO, @"shouldn't happen");
  456. return nil;
  457. }
  458. break;
  459. case GPBDataTypeString:
  460. switch (valueDataType) {
  461. case GPBDataTypeBool:
  462. result = [[GPBStringBoolDictionary alloc] init];
  463. break;
  464. case GPBDataTypeFixed32:
  465. case GPBDataTypeUInt32:
  466. result = [[GPBStringUInt32Dictionary alloc] init];
  467. break;
  468. case GPBDataTypeInt32:
  469. case GPBDataTypeSFixed32:
  470. case GPBDataTypeSInt32:
  471. result = [[GPBStringInt32Dictionary alloc] init];
  472. break;
  473. case GPBDataTypeFixed64:
  474. case GPBDataTypeUInt64:
  475. result = [[GPBStringUInt64Dictionary alloc] init];
  476. break;
  477. case GPBDataTypeInt64:
  478. case GPBDataTypeSFixed64:
  479. case GPBDataTypeSInt64:
  480. result = [[GPBStringInt64Dictionary alloc] init];
  481. break;
  482. case GPBDataTypeFloat:
  483. result = [[GPBStringFloatDictionary alloc] init];
  484. break;
  485. case GPBDataTypeDouble:
  486. result = [[GPBStringDoubleDictionary alloc] init];
  487. break;
  488. case GPBDataTypeEnum:
  489. result = [[GPBStringEnumDictionary alloc]
  490. initWithValidationFunction:field.enumDescriptor.enumVerifier];
  491. break;
  492. case GPBDataTypeBytes:
  493. case GPBDataTypeMessage:
  494. case GPBDataTypeString:
  495. if (autocreator) {
  496. result = [[GPBAutocreatedDictionary alloc] init];
  497. } else {
  498. result = [[NSMutableDictionary alloc] init];
  499. }
  500. break;
  501. case GPBDataTypeGroup:
  502. NSCAssert(NO, @"shouldn't happen");
  503. return nil;
  504. }
  505. break;
  506. case GPBDataTypeFloat:
  507. case GPBDataTypeDouble:
  508. case GPBDataTypeEnum:
  509. case GPBDataTypeBytes:
  510. case GPBDataTypeGroup:
  511. case GPBDataTypeMessage:
  512. NSCAssert(NO, @"shouldn't happen");
  513. return nil;
  514. }
  515. if (autocreator) {
  516. if ((keyDataType == GPBDataTypeString) &&
  517. GPBDataTypeIsObject(valueDataType)) {
  518. GPBAutocreatedDictionary *autoDict = result;
  519. autoDict->_autocreator = autocreator;
  520. } else {
  521. GPBInt32Int32Dictionary *gpbDict = result;
  522. gpbDict->_autocreator = autocreator;
  523. }
  524. }
  525. return result;
  526. }
  527. #if !defined(__clang_analyzer__)
  528. // These functions are blocked from the analyzer because the analyzer sees the
  529. // GPBSetRetainedObjectIvarWithFieldPrivate() call as consuming the array/map,
  530. // so use of the array/map after the call returns is flagged as a use after
  531. // free.
  532. // But GPBSetRetainedObjectIvarWithFieldPrivate() is "consuming" the retain
  533. // count be holding onto the object (it is transferring it), the object is
  534. // still valid after returning from the call. The other way to avoid this
  535. // would be to add a -retain/-autorelease, but that would force every
  536. // repeated/map field parsed into the autorelease pool which is both a memory
  537. // and performance hit.
  538. static id GetOrCreateArrayIvarWithField(GPBMessage *self,
  539. GPBFieldDescriptor *field) {
  540. id array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  541. if (!array) {
  542. // No lock needed, this is called from places expecting to mutate
  543. // so no threading protection is needed.
  544. array = CreateArrayForField(field, nil);
  545. GPBSetRetainedObjectIvarWithFieldPrivate(self, field, array);
  546. }
  547. return array;
  548. }
  549. // This is like GPBGetObjectIvarWithField(), but for arrays, it should
  550. // only be used to wire the method into the class.
  551. static id GetArrayIvarWithField(GPBMessage *self, GPBFieldDescriptor *field) {
  552. id array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  553. if (!array) {
  554. // Check again after getting the lock.
  555. GPBPrepareReadOnlySemaphore(self);
  556. dispatch_semaphore_wait(self->readOnlySemaphore_, DISPATCH_TIME_FOREVER);
  557. array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  558. if (!array) {
  559. array = CreateArrayForField(field, self);
  560. GPBSetAutocreatedRetainedObjectIvarWithField(self, field, array);
  561. }
  562. dispatch_semaphore_signal(self->readOnlySemaphore_);
  563. }
  564. return array;
  565. }
  566. static id GetOrCreateMapIvarWithField(GPBMessage *self,
  567. GPBFieldDescriptor *field) {
  568. id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  569. if (!dict) {
  570. // No lock needed, this is called from places expecting to mutate
  571. // so no threading protection is needed.
  572. dict = CreateMapForField(field, nil);
  573. GPBSetRetainedObjectIvarWithFieldPrivate(self, field, dict);
  574. }
  575. return dict;
  576. }
  577. // This is like GPBGetObjectIvarWithField(), but for maps, it should
  578. // only be used to wire the method into the class.
  579. static id GetMapIvarWithField(GPBMessage *self, GPBFieldDescriptor *field) {
  580. id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  581. if (!dict) {
  582. // Check again after getting the lock.
  583. GPBPrepareReadOnlySemaphore(self);
  584. dispatch_semaphore_wait(self->readOnlySemaphore_, DISPATCH_TIME_FOREVER);
  585. dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  586. if (!dict) {
  587. dict = CreateMapForField(field, self);
  588. GPBSetAutocreatedRetainedObjectIvarWithField(self, field, dict);
  589. }
  590. dispatch_semaphore_signal(self->readOnlySemaphore_);
  591. }
  592. return dict;
  593. }
  594. #endif // !defined(__clang_analyzer__)
  595. GPBMessage *GPBCreateMessageWithAutocreator(Class msgClass,
  596. GPBMessage *autocreator,
  597. GPBFieldDescriptor *field) {
  598. GPBMessage *message = [[msgClass alloc] init];
  599. message->autocreator_ = autocreator;
  600. message->autocreatorField_ = [field retain];
  601. return message;
  602. }
  603. static GPBMessage *CreateMessageWithAutocreatorForExtension(
  604. Class msgClass, GPBMessage *autocreator, GPBExtensionDescriptor *extension)
  605. __attribute__((ns_returns_retained));
  606. static GPBMessage *CreateMessageWithAutocreatorForExtension(
  607. Class msgClass, GPBMessage *autocreator,
  608. GPBExtensionDescriptor *extension) {
  609. GPBMessage *message = [[msgClass alloc] init];
  610. message->autocreator_ = autocreator;
  611. message->autocreatorExtension_ = [extension retain];
  612. return message;
  613. }
  614. BOOL GPBWasMessageAutocreatedBy(GPBMessage *message, GPBMessage *parent) {
  615. return (message->autocreator_ == parent);
  616. }
  617. void GPBBecomeVisibleToAutocreator(GPBMessage *self) {
  618. // Message objects that are implicitly created by accessing a message field
  619. // are initially not visible via the hasX selector. This method makes them
  620. // visible.
  621. if (self->autocreator_) {
  622. // This will recursively make all parent messages visible until it reaches a
  623. // super-creator that's visible.
  624. if (self->autocreatorField_) {
  625. GPBSetObjectIvarWithFieldPrivate(self->autocreator_,
  626. self->autocreatorField_, self);
  627. } else {
  628. [self->autocreator_ setExtension:self->autocreatorExtension_ value:self];
  629. }
  630. }
  631. }
  632. void GPBAutocreatedArrayModified(GPBMessage *self, id array) {
  633. // When one of our autocreated arrays adds elements, make it visible.
  634. GPBDescriptor *descriptor = [[self class] descriptor];
  635. for (GPBFieldDescriptor *field in descriptor->fields_) {
  636. if (field.fieldType == GPBFieldTypeRepeated) {
  637. id curArray = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  638. if (curArray == array) {
  639. if (GPBFieldDataTypeIsObject(field)) {
  640. GPBAutocreatedArray *autoArray = array;
  641. autoArray->_autocreator = nil;
  642. } else {
  643. GPBInt32Array *gpbArray = array;
  644. gpbArray->_autocreator = nil;
  645. }
  646. GPBBecomeVisibleToAutocreator(self);
  647. return;
  648. }
  649. }
  650. }
  651. NSCAssert(NO, @"Unknown autocreated %@ for %@.", [array class], self);
  652. }
  653. void GPBAutocreatedDictionaryModified(GPBMessage *self, id dictionary) {
  654. // When one of our autocreated dicts adds elements, make it visible.
  655. GPBDescriptor *descriptor = [[self class] descriptor];
  656. for (GPBFieldDescriptor *field in descriptor->fields_) {
  657. if (field.fieldType == GPBFieldTypeMap) {
  658. id curDict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  659. if (curDict == dictionary) {
  660. if ((field.mapKeyDataType == GPBDataTypeString) &&
  661. GPBFieldDataTypeIsObject(field)) {
  662. GPBAutocreatedDictionary *autoDict = dictionary;
  663. autoDict->_autocreator = nil;
  664. } else {
  665. GPBInt32Int32Dictionary *gpbDict = dictionary;
  666. gpbDict->_autocreator = nil;
  667. }
  668. GPBBecomeVisibleToAutocreator(self);
  669. return;
  670. }
  671. }
  672. }
  673. NSCAssert(NO, @"Unknown autocreated %@ for %@.", [dictionary class], self);
  674. }
  675. void GPBClearMessageAutocreator(GPBMessage *self) {
  676. if ((self == nil) || !self->autocreator_) {
  677. return;
  678. }
  679. #if defined(DEBUG) && DEBUG && !defined(NS_BLOCK_ASSERTIONS)
  680. // Either the autocreator must have its "has" flag set to YES, or it must be
  681. // NO and not equal to ourselves.
  682. BOOL autocreatorHas =
  683. (self->autocreatorField_
  684. ? GPBGetHasIvarField(self->autocreator_, self->autocreatorField_)
  685. : [self->autocreator_ hasExtension:self->autocreatorExtension_]);
  686. GPBMessage *autocreatorFieldValue =
  687. (self->autocreatorField_
  688. ? GPBGetObjectIvarWithFieldNoAutocreate(self->autocreator_,
  689. self->autocreatorField_)
  690. : [self->autocreator_->autocreatedExtensionMap_
  691. objectForKey:self->autocreatorExtension_]);
  692. NSCAssert(autocreatorHas || autocreatorFieldValue != self,
  693. @"Cannot clear autocreator because it still refers to self, self: %@.",
  694. self);
  695. #endif // DEBUG && !defined(NS_BLOCK_ASSERTIONS)
  696. self->autocreator_ = nil;
  697. [self->autocreatorField_ release];
  698. self->autocreatorField_ = nil;
  699. [self->autocreatorExtension_ release];
  700. self->autocreatorExtension_ = nil;
  701. }
  702. // Call this before using the readOnlySemaphore_. This ensures it is created only once.
  703. void GPBPrepareReadOnlySemaphore(GPBMessage *self) {
  704. #pragma clang diagnostic push
  705. #pragma clang diagnostic ignored "-Wdirect-ivar-access"
  706. // Create the semaphore on demand (rather than init) as developers might not cause them
  707. // to be needed, and the heap usage can add up. The atomic swap is used to avoid needing
  708. // another lock around creating it.
  709. if (self->readOnlySemaphore_ == nil) {
  710. dispatch_semaphore_t worker = dispatch_semaphore_create(1);
  711. dispatch_semaphore_t expected = nil;
  712. if (!atomic_compare_exchange_strong(&self->readOnlySemaphore_, &expected, worker)) {
  713. dispatch_release(worker);
  714. }
  715. #if defined(__clang_analyzer__)
  716. // The Xcode 9.2 (and 9.3 beta) static analyzer thinks worker is leaked
  717. // (doesn't seem to know about atomic_compare_exchange_strong); so just
  718. // for the analyzer, let it think worker is also released in this case.
  719. else { dispatch_release(worker); }
  720. #endif
  721. }
  722. #pragma clang diagnostic pop
  723. }
  724. static GPBUnknownFieldSet *GetOrMakeUnknownFields(GPBMessage *self) {
  725. if (!self->unknownFields_) {
  726. self->unknownFields_ = [[GPBUnknownFieldSet alloc] init];
  727. GPBBecomeVisibleToAutocreator(self);
  728. }
  729. return self->unknownFields_;
  730. }
  731. @implementation GPBMessage
  732. + (void)initialize {
  733. Class pbMessageClass = [GPBMessage class];
  734. if ([self class] == pbMessageClass) {
  735. // This is here to start up the "base" class descriptor.
  736. [self descriptor];
  737. // Message shares extension method resolving with GPBRootObject so insure
  738. // it is started up at the same time.
  739. (void)[GPBRootObject class];
  740. } else if ([self superclass] == pbMessageClass) {
  741. // This is here to start up all the "message" subclasses. Just needs to be
  742. // done for the messages, not any of the subclasses.
  743. // This must be done in initialize to enforce thread safety of start up of
  744. // the protocol buffer library.
  745. // Note: The generated code for -descriptor calls
  746. // +[GPBDescriptor allocDescriptorForClass:...], passing the GPBRootObject
  747. // subclass for the file. That call chain is what ensures that *Root class
  748. // is started up to support extension resolution off the message class
  749. // (+resolveClassMethod: below) in a thread safe manner.
  750. [self descriptor];
  751. }
  752. }
  753. + (instancetype)allocWithZone:(NSZone *)zone {
  754. // Override alloc to allocate our classes with the additional storage
  755. // required for the instance variables.
  756. GPBDescriptor *descriptor = [self descriptor];
  757. return NSAllocateObject(self, descriptor->storageSize_, zone);
  758. }
  759. + (instancetype)alloc {
  760. return [self allocWithZone:nil];
  761. }
  762. + (GPBDescriptor *)descriptor {
  763. // This is thread safe because it is called from +initialize.
  764. static GPBDescriptor *descriptor = NULL;
  765. static GPBFileDescriptor *fileDescriptor = NULL;
  766. if (!descriptor) {
  767. // Use a dummy file that marks it as proto2 syntax so when used generically
  768. // it supports unknowns/etc.
  769. fileDescriptor =
  770. [[GPBFileDescriptor alloc] initWithPackage:@"internal"
  771. syntax:GPBFileSyntaxProto2];
  772. descriptor = [GPBDescriptor allocDescriptorForClass:[GPBMessage class]
  773. rootClass:Nil
  774. file:fileDescriptor
  775. fields:NULL
  776. fieldCount:0
  777. storageSize:0
  778. flags:0];
  779. }
  780. return descriptor;
  781. }
  782. + (instancetype)message {
  783. return [[[self alloc] init] autorelease];
  784. }
  785. - (instancetype)init {
  786. if ((self = [super init])) {
  787. messageStorage_ = (GPBMessage_StoragePtr)(
  788. ((uint8_t *)self) + class_getInstanceSize([self class]));
  789. }
  790. return self;
  791. }
  792. - (instancetype)initWithData:(NSData *)data error:(NSError **)errorPtr {
  793. return [self initWithData:data extensionRegistry:nil error:errorPtr];
  794. }
  795. - (instancetype)initWithData:(NSData *)data
  796. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry
  797. error:(NSError **)errorPtr {
  798. if ((self = [self init])) {
  799. @try {
  800. [self mergeFromData:data extensionRegistry:extensionRegistry];
  801. if (errorPtr) {
  802. *errorPtr = nil;
  803. }
  804. }
  805. @catch (NSException *exception) {
  806. [self release];
  807. self = nil;
  808. if (errorPtr) {
  809. *errorPtr = ErrorFromException(exception);
  810. }
  811. }
  812. #ifdef DEBUG
  813. if (self && !self.initialized) {
  814. [self release];
  815. self = nil;
  816. if (errorPtr) {
  817. *errorPtr = MessageError(GPBMessageErrorCodeMissingRequiredField, nil);
  818. }
  819. }
  820. #endif
  821. }
  822. return self;
  823. }
  824. - (instancetype)initWithCodedInputStream:(GPBCodedInputStream *)input
  825. extensionRegistry:
  826. (GPBExtensionRegistry *)extensionRegistry
  827. error:(NSError **)errorPtr {
  828. if ((self = [self init])) {
  829. @try {
  830. [self mergeFromCodedInputStream:input extensionRegistry:extensionRegistry];
  831. if (errorPtr) {
  832. *errorPtr = nil;
  833. }
  834. }
  835. @catch (NSException *exception) {
  836. [self release];
  837. self = nil;
  838. if (errorPtr) {
  839. *errorPtr = ErrorFromException(exception);
  840. }
  841. }
  842. #ifdef DEBUG
  843. if (self && !self.initialized) {
  844. [self release];
  845. self = nil;
  846. if (errorPtr) {
  847. *errorPtr = MessageError(GPBMessageErrorCodeMissingRequiredField, nil);
  848. }
  849. }
  850. #endif
  851. }
  852. return self;
  853. }
  854. - (void)dealloc {
  855. [self internalClear:NO];
  856. NSCAssert(!autocreator_, @"Autocreator was not cleared before dealloc.");
  857. if (readOnlySemaphore_) {
  858. dispatch_release(readOnlySemaphore_);
  859. }
  860. [super dealloc];
  861. }
  862. - (void)copyFieldsInto:(GPBMessage *)message
  863. zone:(NSZone *)zone
  864. descriptor:(GPBDescriptor *)descriptor {
  865. // Copy all the storage...
  866. memcpy(message->messageStorage_, messageStorage_, descriptor->storageSize_);
  867. // Loop over the fields doing fixup...
  868. for (GPBFieldDescriptor *field in descriptor->fields_) {
  869. if (GPBFieldIsMapOrArray(field)) {
  870. id value = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  871. if (value) {
  872. // We need to copy the array/map, but the catch is for message fields,
  873. // we also need to ensure all the messages as those need copying also.
  874. id newValue;
  875. if (GPBFieldDataTypeIsMessage(field)) {
  876. if (field.fieldType == GPBFieldTypeRepeated) {
  877. NSArray *existingArray = (NSArray *)value;
  878. NSMutableArray *newArray =
  879. [[NSMutableArray alloc] initWithCapacity:existingArray.count];
  880. newValue = newArray;
  881. for (GPBMessage *msg in existingArray) {
  882. GPBMessage *copiedMsg = [msg copyWithZone:zone];
  883. [newArray addObject:copiedMsg];
  884. [copiedMsg release];
  885. }
  886. } else {
  887. if (field.mapKeyDataType == GPBDataTypeString) {
  888. // Map is an NSDictionary.
  889. NSDictionary *existingDict = value;
  890. NSMutableDictionary *newDict = [[NSMutableDictionary alloc]
  891. initWithCapacity:existingDict.count];
  892. newValue = newDict;
  893. [existingDict enumerateKeysAndObjectsUsingBlock:^(NSString *key,
  894. GPBMessage *msg,
  895. BOOL *stop) {
  896. #pragma unused(stop)
  897. GPBMessage *copiedMsg = [msg copyWithZone:zone];
  898. [newDict setObject:copiedMsg forKey:key];
  899. [copiedMsg release];
  900. }];
  901. } else {
  902. // Is one of the GPB*ObjectDictionary classes. Type doesn't
  903. // matter, just need one to invoke the selector.
  904. GPBInt32ObjectDictionary *existingDict = value;
  905. newValue = [existingDict deepCopyWithZone:zone];
  906. }
  907. }
  908. } else {
  909. // Not messages (but is a map/array)...
  910. if (field.fieldType == GPBFieldTypeRepeated) {
  911. if (GPBFieldDataTypeIsObject(field)) {
  912. // NSArray
  913. newValue = [value mutableCopyWithZone:zone];
  914. } else {
  915. // GPB*Array
  916. newValue = [value copyWithZone:zone];
  917. }
  918. } else {
  919. if ((field.mapKeyDataType == GPBDataTypeString) &&
  920. GPBFieldDataTypeIsObject(field)) {
  921. // NSDictionary
  922. newValue = [value mutableCopyWithZone:zone];
  923. } else {
  924. // Is one of the GPB*Dictionary classes. Type doesn't matter,
  925. // just need one to invoke the selector.
  926. GPBInt32Int32Dictionary *existingDict = value;
  927. newValue = [existingDict copyWithZone:zone];
  928. }
  929. }
  930. }
  931. // We retain here because the memcpy picked up the pointer value and
  932. // the next call to SetRetainedObject... will release the current value.
  933. [value retain];
  934. GPBSetRetainedObjectIvarWithFieldPrivate(message, field, newValue);
  935. }
  936. } else if (GPBFieldDataTypeIsMessage(field)) {
  937. // For object types, if we have a value, copy it. If we don't,
  938. // zero it to remove the pointer to something that was autocreated
  939. // (and the ptr just got memcpyed).
  940. if (GPBGetHasIvarField(self, field)) {
  941. GPBMessage *value = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  942. GPBMessage *newValue = [value copyWithZone:zone];
  943. // We retain here because the memcpy picked up the pointer value and
  944. // the next call to SetRetainedObject... will release the current value.
  945. [value retain];
  946. GPBSetRetainedObjectIvarWithFieldPrivate(message, field, newValue);
  947. } else {
  948. uint8_t *storage = (uint8_t *)message->messageStorage_;
  949. id *typePtr = (id *)&storage[field->description_->offset];
  950. *typePtr = NULL;
  951. }
  952. } else if (GPBFieldDataTypeIsObject(field) &&
  953. GPBGetHasIvarField(self, field)) {
  954. // A set string/data value (message picked off above), copy it.
  955. id value = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  956. id newValue = [value copyWithZone:zone];
  957. // We retain here because the memcpy picked up the pointer value and
  958. // the next call to SetRetainedObject... will release the current value.
  959. [value retain];
  960. GPBSetRetainedObjectIvarWithFieldPrivate(message, field, newValue);
  961. } else {
  962. // memcpy took care of the rest of the primitive fields if they were set.
  963. }
  964. } // for (field in descriptor->fields_)
  965. }
  966. - (id)copyWithZone:(NSZone *)zone {
  967. GPBDescriptor *descriptor = [self descriptor];
  968. GPBMessage *result = [[descriptor.messageClass allocWithZone:zone] init];
  969. [self copyFieldsInto:result zone:zone descriptor:descriptor];
  970. // Make immutable copies of the extra bits.
  971. result->unknownFields_ = [unknownFields_ copyWithZone:zone];
  972. result->extensionMap_ = CloneExtensionMap(extensionMap_, zone);
  973. return result;
  974. }
  975. - (void)clear {
  976. [self internalClear:YES];
  977. }
  978. - (void)internalClear:(BOOL)zeroStorage {
  979. GPBDescriptor *descriptor = [self descriptor];
  980. for (GPBFieldDescriptor *field in descriptor->fields_) {
  981. if (GPBFieldIsMapOrArray(field)) {
  982. id arrayOrMap = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  983. if (arrayOrMap) {
  984. if (field.fieldType == GPBFieldTypeRepeated) {
  985. if (GPBFieldDataTypeIsObject(field)) {
  986. if ([arrayOrMap isKindOfClass:[GPBAutocreatedArray class]]) {
  987. GPBAutocreatedArray *autoArray = arrayOrMap;
  988. if (autoArray->_autocreator == self) {
  989. autoArray->_autocreator = nil;
  990. }
  991. }
  992. } else {
  993. // Type doesn't matter, it is a GPB*Array.
  994. GPBInt32Array *gpbArray = arrayOrMap;
  995. if (gpbArray->_autocreator == self) {
  996. gpbArray->_autocreator = nil;
  997. }
  998. }
  999. } else {
  1000. if ((field.mapKeyDataType == GPBDataTypeString) &&
  1001. GPBFieldDataTypeIsObject(field)) {
  1002. if ([arrayOrMap isKindOfClass:[GPBAutocreatedDictionary class]]) {
  1003. GPBAutocreatedDictionary *autoDict = arrayOrMap;
  1004. if (autoDict->_autocreator == self) {
  1005. autoDict->_autocreator = nil;
  1006. }
  1007. }
  1008. } else {
  1009. // Type doesn't matter, it is a GPB*Dictionary.
  1010. GPBInt32Int32Dictionary *gpbDict = arrayOrMap;
  1011. if (gpbDict->_autocreator == self) {
  1012. gpbDict->_autocreator = nil;
  1013. }
  1014. }
  1015. }
  1016. [arrayOrMap release];
  1017. }
  1018. } else if (GPBFieldDataTypeIsMessage(field)) {
  1019. GPBClearAutocreatedMessageIvarWithField(self, field);
  1020. GPBMessage *value = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1021. [value release];
  1022. } else if (GPBFieldDataTypeIsObject(field) &&
  1023. GPBGetHasIvarField(self, field)) {
  1024. id value = GPBGetObjectIvarWithField(self, field);
  1025. [value release];
  1026. }
  1027. }
  1028. // GPBClearMessageAutocreator() expects that its caller has already been
  1029. // removed from autocreatedExtensionMap_ so we set to nil first.
  1030. NSArray *autocreatedValues = [autocreatedExtensionMap_ allValues];
  1031. [autocreatedExtensionMap_ release];
  1032. autocreatedExtensionMap_ = nil;
  1033. // Since we're clearing all of our extensions, make sure that we clear the
  1034. // autocreator on any that we've created so they no longer refer to us.
  1035. for (GPBMessage *value in autocreatedValues) {
  1036. NSCAssert(GPBWasMessageAutocreatedBy(value, self),
  1037. @"Autocreated extension does not refer back to self.");
  1038. GPBClearMessageAutocreator(value);
  1039. }
  1040. [extensionMap_ release];
  1041. extensionMap_ = nil;
  1042. [unknownFields_ release];
  1043. unknownFields_ = nil;
  1044. // Note that clearing does not affect autocreator_. If we are being cleared
  1045. // because of a dealloc, then autocreator_ should be nil anyway. If we are
  1046. // being cleared because someone explicitly clears us, we don't want to
  1047. // sever our relationship with our autocreator.
  1048. if (zeroStorage) {
  1049. memset(messageStorage_, 0, descriptor->storageSize_);
  1050. }
  1051. }
  1052. - (BOOL)isInitialized {
  1053. GPBDescriptor *descriptor = [self descriptor];
  1054. for (GPBFieldDescriptor *field in descriptor->fields_) {
  1055. if (field.isRequired) {
  1056. if (!GPBGetHasIvarField(self, field)) {
  1057. return NO;
  1058. }
  1059. }
  1060. if (GPBFieldDataTypeIsMessage(field)) {
  1061. GPBFieldType fieldType = field.fieldType;
  1062. if (fieldType == GPBFieldTypeSingle) {
  1063. if (field.isRequired) {
  1064. GPBMessage *message = GPBGetMessageMessageField(self, field);
  1065. if (!message.initialized) {
  1066. return NO;
  1067. }
  1068. } else {
  1069. NSAssert(field.isOptional,
  1070. @"%@: Single message field %@ not required or optional?",
  1071. [self class], field.name);
  1072. if (GPBGetHasIvarField(self, field)) {
  1073. GPBMessage *message = GPBGetMessageMessageField(self, field);
  1074. if (!message.initialized) {
  1075. return NO;
  1076. }
  1077. }
  1078. }
  1079. } else if (fieldType == GPBFieldTypeRepeated) {
  1080. NSArray *array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1081. for (GPBMessage *message in array) {
  1082. if (!message.initialized) {
  1083. return NO;
  1084. }
  1085. }
  1086. } else { // fieldType == GPBFieldTypeMap
  1087. if (field.mapKeyDataType == GPBDataTypeString) {
  1088. NSDictionary *map =
  1089. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1090. if (map && !GPBDictionaryIsInitializedInternalHelper(map, field)) {
  1091. return NO;
  1092. }
  1093. } else {
  1094. // Real type is GPB*ObjectDictionary, exact type doesn't matter.
  1095. GPBInt32ObjectDictionary *map =
  1096. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1097. if (map && ![map isInitialized]) {
  1098. return NO;
  1099. }
  1100. }
  1101. }
  1102. }
  1103. }
  1104. __block BOOL result = YES;
  1105. [extensionMap_
  1106. enumerateKeysAndObjectsUsingBlock:^(GPBExtensionDescriptor *extension,
  1107. id obj,
  1108. BOOL *stop) {
  1109. if (GPBExtensionIsMessage(extension)) {
  1110. if (extension.isRepeated) {
  1111. for (GPBMessage *msg in obj) {
  1112. if (!msg.initialized) {
  1113. result = NO;
  1114. *stop = YES;
  1115. break;
  1116. }
  1117. }
  1118. } else {
  1119. GPBMessage *asMsg = obj;
  1120. if (!asMsg.initialized) {
  1121. result = NO;
  1122. *stop = YES;
  1123. }
  1124. }
  1125. }
  1126. }];
  1127. return result;
  1128. }
  1129. - (GPBDescriptor *)descriptor {
  1130. return [[self class] descriptor];
  1131. }
  1132. - (NSData *)data {
  1133. #ifdef DEBUG
  1134. if (!self.initialized) {
  1135. return nil;
  1136. }
  1137. #endif
  1138. NSMutableData *data = [NSMutableData dataWithLength:[self serializedSize]];
  1139. GPBCodedOutputStream *stream =
  1140. [[GPBCodedOutputStream alloc] initWithData:data];
  1141. @try {
  1142. [self writeToCodedOutputStream:stream];
  1143. }
  1144. @catch (NSException *exception) {
  1145. // This really shouldn't happen. The only way writeToCodedOutputStream:
  1146. // could throw is if something in the library has a bug and the
  1147. // serializedSize was wrong.
  1148. #ifdef DEBUG
  1149. NSLog(@"%@: Internal exception while building message data: %@",
  1150. [self class], exception);
  1151. #endif
  1152. data = nil;
  1153. }
  1154. [stream release];
  1155. return data;
  1156. }
  1157. - (NSData *)delimitedData {
  1158. size_t serializedSize = [self serializedSize];
  1159. size_t varintSize = GPBComputeRawVarint32SizeForInteger(serializedSize);
  1160. NSMutableData *data =
  1161. [NSMutableData dataWithLength:(serializedSize + varintSize)];
  1162. GPBCodedOutputStream *stream =
  1163. [[GPBCodedOutputStream alloc] initWithData:data];
  1164. @try {
  1165. [self writeDelimitedToCodedOutputStream:stream];
  1166. }
  1167. @catch (NSException *exception) {
  1168. // This really shouldn't happen. The only way writeToCodedOutputStream:
  1169. // could throw is if something in the library has a bug and the
  1170. // serializedSize was wrong.
  1171. #ifdef DEBUG
  1172. NSLog(@"%@: Internal exception while building message delimitedData: %@",
  1173. [self class], exception);
  1174. #endif
  1175. // If it happens, truncate.
  1176. data.length = 0;
  1177. }
  1178. [stream release];
  1179. return data;
  1180. }
  1181. - (void)writeToOutputStream:(NSOutputStream *)output {
  1182. GPBCodedOutputStream *stream =
  1183. [[GPBCodedOutputStream alloc] initWithOutputStream:output];
  1184. [self writeToCodedOutputStream:stream];
  1185. [stream release];
  1186. }
  1187. - (void)writeToCodedOutputStream:(GPBCodedOutputStream *)output {
  1188. GPBDescriptor *descriptor = [self descriptor];
  1189. NSArray *fieldsArray = descriptor->fields_;
  1190. NSUInteger fieldCount = fieldsArray.count;
  1191. const GPBExtensionRange *extensionRanges = descriptor.extensionRanges;
  1192. NSUInteger extensionRangesCount = descriptor.extensionRangesCount;
  1193. NSArray *sortedExtensions =
  1194. [[extensionMap_ allKeys] sortedArrayUsingSelector:@selector(compareByFieldNumber:)];
  1195. for (NSUInteger i = 0, j = 0; i < fieldCount || j < extensionRangesCount;) {
  1196. if (i == fieldCount) {
  1197. [self writeExtensionsToCodedOutputStream:output
  1198. range:extensionRanges[j++]
  1199. sortedExtensions:sortedExtensions];
  1200. } else if (j == extensionRangesCount ||
  1201. GPBFieldNumber(fieldsArray[i]) < extensionRanges[j].start) {
  1202. [self writeField:fieldsArray[i++] toCodedOutputStream:output];
  1203. } else {
  1204. [self writeExtensionsToCodedOutputStream:output
  1205. range:extensionRanges[j++]
  1206. sortedExtensions:sortedExtensions];
  1207. }
  1208. }
  1209. if (descriptor.isWireFormat) {
  1210. [unknownFields_ writeAsMessageSetTo:output];
  1211. } else {
  1212. [unknownFields_ writeToCodedOutputStream:output];
  1213. }
  1214. }
  1215. - (void)writeDelimitedToOutputStream:(NSOutputStream *)output {
  1216. GPBCodedOutputStream *codedOutput =
  1217. [[GPBCodedOutputStream alloc] initWithOutputStream:output];
  1218. [self writeDelimitedToCodedOutputStream:codedOutput];
  1219. [codedOutput release];
  1220. }
  1221. - (void)writeDelimitedToCodedOutputStream:(GPBCodedOutputStream *)output {
  1222. [output writeRawVarintSizeTAs32:[self serializedSize]];
  1223. [self writeToCodedOutputStream:output];
  1224. }
  1225. - (void)writeField:(GPBFieldDescriptor *)field
  1226. toCodedOutputStream:(GPBCodedOutputStream *)output {
  1227. GPBFieldType fieldType = field.fieldType;
  1228. if (fieldType == GPBFieldTypeSingle) {
  1229. BOOL has = GPBGetHasIvarField(self, field);
  1230. if (!has) {
  1231. return;
  1232. }
  1233. }
  1234. uint32_t fieldNumber = GPBFieldNumber(field);
  1235. //%PDDM-DEFINE FIELD_CASE(TYPE, REAL_TYPE)
  1236. //%FIELD_CASE_FULL(TYPE, REAL_TYPE, REAL_TYPE)
  1237. //%PDDM-DEFINE FIELD_CASE_FULL(TYPE, REAL_TYPE, ARRAY_TYPE)
  1238. //% case GPBDataType##TYPE:
  1239. //% if (fieldType == GPBFieldTypeRepeated) {
  1240. //% uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1241. //% GPB##ARRAY_TYPE##Array *array =
  1242. //% GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1243. //% [output write##TYPE##Array:fieldNumber values:array tag:tag];
  1244. //% } else if (fieldType == GPBFieldTypeSingle) {
  1245. //% [output write##TYPE:fieldNumber
  1246. //% TYPE$S value:GPBGetMessage##REAL_TYPE##Field(self, field)];
  1247. //% } else { // fieldType == GPBFieldTypeMap
  1248. //% // Exact type here doesn't matter.
  1249. //% GPBInt32##ARRAY_TYPE##Dictionary *dict =
  1250. //% GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1251. //% [dict writeToCodedOutputStream:output asField:field];
  1252. //% }
  1253. //% break;
  1254. //%
  1255. //%PDDM-DEFINE FIELD_CASE2(TYPE)
  1256. //% case GPBDataType##TYPE:
  1257. //% if (fieldType == GPBFieldTypeRepeated) {
  1258. //% NSArray *array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1259. //% [output write##TYPE##Array:fieldNumber values:array];
  1260. //% } else if (fieldType == GPBFieldTypeSingle) {
  1261. //% // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has check
  1262. //% // again.
  1263. //% [output write##TYPE:fieldNumber
  1264. //% TYPE$S value:GPBGetObjectIvarWithFieldNoAutocreate(self, field)];
  1265. //% } else { // fieldType == GPBFieldTypeMap
  1266. //% // Exact type here doesn't matter.
  1267. //% id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1268. //% GPBDataType mapKeyDataType = field.mapKeyDataType;
  1269. //% if (mapKeyDataType == GPBDataTypeString) {
  1270. //% GPBDictionaryWriteToStreamInternalHelper(output, dict, field);
  1271. //% } else {
  1272. //% [dict writeToCodedOutputStream:output asField:field];
  1273. //% }
  1274. //% }
  1275. //% break;
  1276. //%
  1277. switch (GPBGetFieldDataType(field)) {
  1278. //%PDDM-EXPAND FIELD_CASE(Bool, Bool)
  1279. // This block of code is generated, do not edit it directly.
  1280. // clang-format off
  1281. case GPBDataTypeBool:
  1282. if (fieldType == GPBFieldTypeRepeated) {
  1283. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1284. GPBBoolArray *array =
  1285. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1286. [output writeBoolArray:fieldNumber values:array tag:tag];
  1287. } else if (fieldType == GPBFieldTypeSingle) {
  1288. [output writeBool:fieldNumber
  1289. value:GPBGetMessageBoolField(self, field)];
  1290. } else { // fieldType == GPBFieldTypeMap
  1291. // Exact type here doesn't matter.
  1292. GPBInt32BoolDictionary *dict =
  1293. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1294. [dict writeToCodedOutputStream:output asField:field];
  1295. }
  1296. break;
  1297. // clang-format on
  1298. //%PDDM-EXPAND FIELD_CASE(Fixed32, UInt32)
  1299. // This block of code is generated, do not edit it directly.
  1300. // clang-format off
  1301. case GPBDataTypeFixed32:
  1302. if (fieldType == GPBFieldTypeRepeated) {
  1303. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1304. GPBUInt32Array *array =
  1305. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1306. [output writeFixed32Array:fieldNumber values:array tag:tag];
  1307. } else if (fieldType == GPBFieldTypeSingle) {
  1308. [output writeFixed32:fieldNumber
  1309. value:GPBGetMessageUInt32Field(self, field)];
  1310. } else { // fieldType == GPBFieldTypeMap
  1311. // Exact type here doesn't matter.
  1312. GPBInt32UInt32Dictionary *dict =
  1313. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1314. [dict writeToCodedOutputStream:output asField:field];
  1315. }
  1316. break;
  1317. // clang-format on
  1318. //%PDDM-EXPAND FIELD_CASE(SFixed32, Int32)
  1319. // This block of code is generated, do not edit it directly.
  1320. // clang-format off
  1321. case GPBDataTypeSFixed32:
  1322. if (fieldType == GPBFieldTypeRepeated) {
  1323. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1324. GPBInt32Array *array =
  1325. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1326. [output writeSFixed32Array:fieldNumber values:array tag:tag];
  1327. } else if (fieldType == GPBFieldTypeSingle) {
  1328. [output writeSFixed32:fieldNumber
  1329. value:GPBGetMessageInt32Field(self, field)];
  1330. } else { // fieldType == GPBFieldTypeMap
  1331. // Exact type here doesn't matter.
  1332. GPBInt32Int32Dictionary *dict =
  1333. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1334. [dict writeToCodedOutputStream:output asField:field];
  1335. }
  1336. break;
  1337. // clang-format on
  1338. //%PDDM-EXPAND FIELD_CASE(Float, Float)
  1339. // This block of code is generated, do not edit it directly.
  1340. // clang-format off
  1341. case GPBDataTypeFloat:
  1342. if (fieldType == GPBFieldTypeRepeated) {
  1343. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1344. GPBFloatArray *array =
  1345. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1346. [output writeFloatArray:fieldNumber values:array tag:tag];
  1347. } else if (fieldType == GPBFieldTypeSingle) {
  1348. [output writeFloat:fieldNumber
  1349. value:GPBGetMessageFloatField(self, field)];
  1350. } else { // fieldType == GPBFieldTypeMap
  1351. // Exact type here doesn't matter.
  1352. GPBInt32FloatDictionary *dict =
  1353. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1354. [dict writeToCodedOutputStream:output asField:field];
  1355. }
  1356. break;
  1357. // clang-format on
  1358. //%PDDM-EXPAND FIELD_CASE(Fixed64, UInt64)
  1359. // This block of code is generated, do not edit it directly.
  1360. // clang-format off
  1361. case GPBDataTypeFixed64:
  1362. if (fieldType == GPBFieldTypeRepeated) {
  1363. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1364. GPBUInt64Array *array =
  1365. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1366. [output writeFixed64Array:fieldNumber values:array tag:tag];
  1367. } else if (fieldType == GPBFieldTypeSingle) {
  1368. [output writeFixed64:fieldNumber
  1369. value:GPBGetMessageUInt64Field(self, field)];
  1370. } else { // fieldType == GPBFieldTypeMap
  1371. // Exact type here doesn't matter.
  1372. GPBInt32UInt64Dictionary *dict =
  1373. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1374. [dict writeToCodedOutputStream:output asField:field];
  1375. }
  1376. break;
  1377. // clang-format on
  1378. //%PDDM-EXPAND FIELD_CASE(SFixed64, Int64)
  1379. // This block of code is generated, do not edit it directly.
  1380. // clang-format off
  1381. case GPBDataTypeSFixed64:
  1382. if (fieldType == GPBFieldTypeRepeated) {
  1383. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1384. GPBInt64Array *array =
  1385. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1386. [output writeSFixed64Array:fieldNumber values:array tag:tag];
  1387. } else if (fieldType == GPBFieldTypeSingle) {
  1388. [output writeSFixed64:fieldNumber
  1389. value:GPBGetMessageInt64Field(self, field)];
  1390. } else { // fieldType == GPBFieldTypeMap
  1391. // Exact type here doesn't matter.
  1392. GPBInt32Int64Dictionary *dict =
  1393. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1394. [dict writeToCodedOutputStream:output asField:field];
  1395. }
  1396. break;
  1397. // clang-format on
  1398. //%PDDM-EXPAND FIELD_CASE(Double, Double)
  1399. // This block of code is generated, do not edit it directly.
  1400. // clang-format off
  1401. case GPBDataTypeDouble:
  1402. if (fieldType == GPBFieldTypeRepeated) {
  1403. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1404. GPBDoubleArray *array =
  1405. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1406. [output writeDoubleArray:fieldNumber values:array tag:tag];
  1407. } else if (fieldType == GPBFieldTypeSingle) {
  1408. [output writeDouble:fieldNumber
  1409. value:GPBGetMessageDoubleField(self, field)];
  1410. } else { // fieldType == GPBFieldTypeMap
  1411. // Exact type here doesn't matter.
  1412. GPBInt32DoubleDictionary *dict =
  1413. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1414. [dict writeToCodedOutputStream:output asField:field];
  1415. }
  1416. break;
  1417. // clang-format on
  1418. //%PDDM-EXPAND FIELD_CASE(Int32, Int32)
  1419. // This block of code is generated, do not edit it directly.
  1420. // clang-format off
  1421. case GPBDataTypeInt32:
  1422. if (fieldType == GPBFieldTypeRepeated) {
  1423. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1424. GPBInt32Array *array =
  1425. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1426. [output writeInt32Array:fieldNumber values:array tag:tag];
  1427. } else if (fieldType == GPBFieldTypeSingle) {
  1428. [output writeInt32:fieldNumber
  1429. value:GPBGetMessageInt32Field(self, field)];
  1430. } else { // fieldType == GPBFieldTypeMap
  1431. // Exact type here doesn't matter.
  1432. GPBInt32Int32Dictionary *dict =
  1433. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1434. [dict writeToCodedOutputStream:output asField:field];
  1435. }
  1436. break;
  1437. // clang-format on
  1438. //%PDDM-EXPAND FIELD_CASE(Int64, Int64)
  1439. // This block of code is generated, do not edit it directly.
  1440. // clang-format off
  1441. case GPBDataTypeInt64:
  1442. if (fieldType == GPBFieldTypeRepeated) {
  1443. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1444. GPBInt64Array *array =
  1445. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1446. [output writeInt64Array:fieldNumber values:array tag:tag];
  1447. } else if (fieldType == GPBFieldTypeSingle) {
  1448. [output writeInt64:fieldNumber
  1449. value:GPBGetMessageInt64Field(self, field)];
  1450. } else { // fieldType == GPBFieldTypeMap
  1451. // Exact type here doesn't matter.
  1452. GPBInt32Int64Dictionary *dict =
  1453. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1454. [dict writeToCodedOutputStream:output asField:field];
  1455. }
  1456. break;
  1457. // clang-format on
  1458. //%PDDM-EXPAND FIELD_CASE(SInt32, Int32)
  1459. // This block of code is generated, do not edit it directly.
  1460. // clang-format off
  1461. case GPBDataTypeSInt32:
  1462. if (fieldType == GPBFieldTypeRepeated) {
  1463. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1464. GPBInt32Array *array =
  1465. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1466. [output writeSInt32Array:fieldNumber values:array tag:tag];
  1467. } else if (fieldType == GPBFieldTypeSingle) {
  1468. [output writeSInt32:fieldNumber
  1469. value:GPBGetMessageInt32Field(self, field)];
  1470. } else { // fieldType == GPBFieldTypeMap
  1471. // Exact type here doesn't matter.
  1472. GPBInt32Int32Dictionary *dict =
  1473. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1474. [dict writeToCodedOutputStream:output asField:field];
  1475. }
  1476. break;
  1477. // clang-format on
  1478. //%PDDM-EXPAND FIELD_CASE(SInt64, Int64)
  1479. // This block of code is generated, do not edit it directly.
  1480. // clang-format off
  1481. case GPBDataTypeSInt64:
  1482. if (fieldType == GPBFieldTypeRepeated) {
  1483. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1484. GPBInt64Array *array =
  1485. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1486. [output writeSInt64Array:fieldNumber values:array tag:tag];
  1487. } else if (fieldType == GPBFieldTypeSingle) {
  1488. [output writeSInt64:fieldNumber
  1489. value:GPBGetMessageInt64Field(self, field)];
  1490. } else { // fieldType == GPBFieldTypeMap
  1491. // Exact type here doesn't matter.
  1492. GPBInt32Int64Dictionary *dict =
  1493. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1494. [dict writeToCodedOutputStream:output asField:field];
  1495. }
  1496. break;
  1497. // clang-format on
  1498. //%PDDM-EXPAND FIELD_CASE(UInt32, UInt32)
  1499. // This block of code is generated, do not edit it directly.
  1500. // clang-format off
  1501. case GPBDataTypeUInt32:
  1502. if (fieldType == GPBFieldTypeRepeated) {
  1503. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1504. GPBUInt32Array *array =
  1505. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1506. [output writeUInt32Array:fieldNumber values:array tag:tag];
  1507. } else if (fieldType == GPBFieldTypeSingle) {
  1508. [output writeUInt32:fieldNumber
  1509. value:GPBGetMessageUInt32Field(self, field)];
  1510. } else { // fieldType == GPBFieldTypeMap
  1511. // Exact type here doesn't matter.
  1512. GPBInt32UInt32Dictionary *dict =
  1513. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1514. [dict writeToCodedOutputStream:output asField:field];
  1515. }
  1516. break;
  1517. // clang-format on
  1518. //%PDDM-EXPAND FIELD_CASE(UInt64, UInt64)
  1519. // This block of code is generated, do not edit it directly.
  1520. // clang-format off
  1521. case GPBDataTypeUInt64:
  1522. if (fieldType == GPBFieldTypeRepeated) {
  1523. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1524. GPBUInt64Array *array =
  1525. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1526. [output writeUInt64Array:fieldNumber values:array tag:tag];
  1527. } else if (fieldType == GPBFieldTypeSingle) {
  1528. [output writeUInt64:fieldNumber
  1529. value:GPBGetMessageUInt64Field(self, field)];
  1530. } else { // fieldType == GPBFieldTypeMap
  1531. // Exact type here doesn't matter.
  1532. GPBInt32UInt64Dictionary *dict =
  1533. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1534. [dict writeToCodedOutputStream:output asField:field];
  1535. }
  1536. break;
  1537. // clang-format on
  1538. //%PDDM-EXPAND FIELD_CASE_FULL(Enum, Int32, Enum)
  1539. // This block of code is generated, do not edit it directly.
  1540. // clang-format off
  1541. case GPBDataTypeEnum:
  1542. if (fieldType == GPBFieldTypeRepeated) {
  1543. uint32_t tag = field.isPackable ? GPBFieldTag(field) : 0;
  1544. GPBEnumArray *array =
  1545. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1546. [output writeEnumArray:fieldNumber values:array tag:tag];
  1547. } else if (fieldType == GPBFieldTypeSingle) {
  1548. [output writeEnum:fieldNumber
  1549. value:GPBGetMessageInt32Field(self, field)];
  1550. } else { // fieldType == GPBFieldTypeMap
  1551. // Exact type here doesn't matter.
  1552. GPBInt32EnumDictionary *dict =
  1553. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1554. [dict writeToCodedOutputStream:output asField:field];
  1555. }
  1556. break;
  1557. // clang-format on
  1558. //%PDDM-EXPAND FIELD_CASE2(Bytes)
  1559. // This block of code is generated, do not edit it directly.
  1560. // clang-format off
  1561. case GPBDataTypeBytes:
  1562. if (fieldType == GPBFieldTypeRepeated) {
  1563. NSArray *array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1564. [output writeBytesArray:fieldNumber values:array];
  1565. } else if (fieldType == GPBFieldTypeSingle) {
  1566. // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has check
  1567. // again.
  1568. [output writeBytes:fieldNumber
  1569. value:GPBGetObjectIvarWithFieldNoAutocreate(self, field)];
  1570. } else { // fieldType == GPBFieldTypeMap
  1571. // Exact type here doesn't matter.
  1572. id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1573. GPBDataType mapKeyDataType = field.mapKeyDataType;
  1574. if (mapKeyDataType == GPBDataTypeString) {
  1575. GPBDictionaryWriteToStreamInternalHelper(output, dict, field);
  1576. } else {
  1577. [dict writeToCodedOutputStream:output asField:field];
  1578. }
  1579. }
  1580. break;
  1581. // clang-format on
  1582. //%PDDM-EXPAND FIELD_CASE2(String)
  1583. // This block of code is generated, do not edit it directly.
  1584. // clang-format off
  1585. case GPBDataTypeString:
  1586. if (fieldType == GPBFieldTypeRepeated) {
  1587. NSArray *array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1588. [output writeStringArray:fieldNumber values:array];
  1589. } else if (fieldType == GPBFieldTypeSingle) {
  1590. // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has check
  1591. // again.
  1592. [output writeString:fieldNumber
  1593. value:GPBGetObjectIvarWithFieldNoAutocreate(self, field)];
  1594. } else { // fieldType == GPBFieldTypeMap
  1595. // Exact type here doesn't matter.
  1596. id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1597. GPBDataType mapKeyDataType = field.mapKeyDataType;
  1598. if (mapKeyDataType == GPBDataTypeString) {
  1599. GPBDictionaryWriteToStreamInternalHelper(output, dict, field);
  1600. } else {
  1601. [dict writeToCodedOutputStream:output asField:field];
  1602. }
  1603. }
  1604. break;
  1605. // clang-format on
  1606. //%PDDM-EXPAND FIELD_CASE2(Message)
  1607. // This block of code is generated, do not edit it directly.
  1608. // clang-format off
  1609. case GPBDataTypeMessage:
  1610. if (fieldType == GPBFieldTypeRepeated) {
  1611. NSArray *array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1612. [output writeMessageArray:fieldNumber values:array];
  1613. } else if (fieldType == GPBFieldTypeSingle) {
  1614. // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has check
  1615. // again.
  1616. [output writeMessage:fieldNumber
  1617. value:GPBGetObjectIvarWithFieldNoAutocreate(self, field)];
  1618. } else { // fieldType == GPBFieldTypeMap
  1619. // Exact type here doesn't matter.
  1620. id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1621. GPBDataType mapKeyDataType = field.mapKeyDataType;
  1622. if (mapKeyDataType == GPBDataTypeString) {
  1623. GPBDictionaryWriteToStreamInternalHelper(output, dict, field);
  1624. } else {
  1625. [dict writeToCodedOutputStream:output asField:field];
  1626. }
  1627. }
  1628. break;
  1629. // clang-format on
  1630. //%PDDM-EXPAND FIELD_CASE2(Group)
  1631. // This block of code is generated, do not edit it directly.
  1632. // clang-format off
  1633. case GPBDataTypeGroup:
  1634. if (fieldType == GPBFieldTypeRepeated) {
  1635. NSArray *array = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1636. [output writeGroupArray:fieldNumber values:array];
  1637. } else if (fieldType == GPBFieldTypeSingle) {
  1638. // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has check
  1639. // again.
  1640. [output writeGroup:fieldNumber
  1641. value:GPBGetObjectIvarWithFieldNoAutocreate(self, field)];
  1642. } else { // fieldType == GPBFieldTypeMap
  1643. // Exact type here doesn't matter.
  1644. id dict = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  1645. GPBDataType mapKeyDataType = field.mapKeyDataType;
  1646. if (mapKeyDataType == GPBDataTypeString) {
  1647. GPBDictionaryWriteToStreamInternalHelper(output, dict, field);
  1648. } else {
  1649. [dict writeToCodedOutputStream:output asField:field];
  1650. }
  1651. }
  1652. break;
  1653. // clang-format on
  1654. //%PDDM-EXPAND-END (18 expansions)
  1655. }
  1656. }
  1657. #pragma mark - Extensions
  1658. - (id)getExtension:(GPBExtensionDescriptor *)extension {
  1659. CheckExtension(self, extension);
  1660. id value = [extensionMap_ objectForKey:extension];
  1661. if (value != nil) {
  1662. return value;
  1663. }
  1664. // No default for repeated.
  1665. if (extension.isRepeated) {
  1666. return nil;
  1667. }
  1668. // Non messages get their default.
  1669. if (!GPBExtensionIsMessage(extension)) {
  1670. return extension.defaultValue;
  1671. }
  1672. // Check for an autocreated value.
  1673. GPBPrepareReadOnlySemaphore(self);
  1674. dispatch_semaphore_wait(readOnlySemaphore_, DISPATCH_TIME_FOREVER);
  1675. value = [autocreatedExtensionMap_ objectForKey:extension];
  1676. if (!value) {
  1677. // Auto create the message extensions to match normal fields.
  1678. value = CreateMessageWithAutocreatorForExtension(extension.msgClass, self,
  1679. extension);
  1680. if (autocreatedExtensionMap_ == nil) {
  1681. autocreatedExtensionMap_ = [[NSMutableDictionary alloc] init];
  1682. }
  1683. // We can't simply call setExtension here because that would clear the new
  1684. // value's autocreator.
  1685. [autocreatedExtensionMap_ setObject:value forKey:extension];
  1686. [value release];
  1687. }
  1688. dispatch_semaphore_signal(readOnlySemaphore_);
  1689. return value;
  1690. }
  1691. - (id)getExistingExtension:(GPBExtensionDescriptor *)extension {
  1692. // This is an internal method so we don't need to call CheckExtension().
  1693. return [extensionMap_ objectForKey:extension];
  1694. }
  1695. - (BOOL)hasExtension:(GPBExtensionDescriptor *)extension {
  1696. #if defined(DEBUG) && DEBUG
  1697. CheckExtension(self, extension);
  1698. #endif // DEBUG
  1699. return nil != [extensionMap_ objectForKey:extension];
  1700. }
  1701. - (NSArray *)extensionsCurrentlySet {
  1702. return [extensionMap_ allKeys];
  1703. }
  1704. - (void)writeExtensionsToCodedOutputStream:(GPBCodedOutputStream *)output
  1705. range:(GPBExtensionRange)range
  1706. sortedExtensions:(NSArray *)sortedExtensions {
  1707. uint32_t start = range.start;
  1708. uint32_t end = range.end;
  1709. for (GPBExtensionDescriptor *extension in sortedExtensions) {
  1710. uint32_t fieldNumber = extension.fieldNumber;
  1711. if (fieldNumber < start) {
  1712. continue;
  1713. }
  1714. if (fieldNumber >= end) {
  1715. break;
  1716. }
  1717. id value = [extensionMap_ objectForKey:extension];
  1718. GPBWriteExtensionValueToOutputStream(extension, value, output);
  1719. }
  1720. }
  1721. - (void)setExtension:(GPBExtensionDescriptor *)extension value:(id)value {
  1722. if (!value) {
  1723. [self clearExtension:extension];
  1724. return;
  1725. }
  1726. CheckExtension(self, extension);
  1727. if (extension.repeated) {
  1728. [NSException raise:NSInvalidArgumentException
  1729. format:@"Must call addExtension() for repeated types."];
  1730. }
  1731. if (extensionMap_ == nil) {
  1732. extensionMap_ = [[NSMutableDictionary alloc] init];
  1733. }
  1734. // This pointless cast is for CLANG_WARN_NULLABLE_TO_NONNULL_CONVERSION.
  1735. // Without it, the compiler complains we're passing an id nullable when
  1736. // setObject:forKey: requires a id nonnull for the value. The check for
  1737. // !value at the start of the method ensures it isn't nil, but the check
  1738. // isn't smart enough to realize that.
  1739. [extensionMap_ setObject:(id)value forKey:extension];
  1740. GPBExtensionDescriptor *descriptor = extension;
  1741. if (GPBExtensionIsMessage(descriptor) && !descriptor.isRepeated) {
  1742. GPBMessage *autocreatedValue =
  1743. [[autocreatedExtensionMap_ objectForKey:extension] retain];
  1744. // Must remove from the map before calling GPBClearMessageAutocreator() so
  1745. // that GPBClearMessageAutocreator() knows its safe to clear.
  1746. [autocreatedExtensionMap_ removeObjectForKey:extension];
  1747. GPBClearMessageAutocreator(autocreatedValue);
  1748. [autocreatedValue release];
  1749. }
  1750. GPBBecomeVisibleToAutocreator(self);
  1751. }
  1752. - (void)addExtension:(GPBExtensionDescriptor *)extension value:(id)value {
  1753. CheckExtension(self, extension);
  1754. if (!extension.repeated) {
  1755. [NSException raise:NSInvalidArgumentException
  1756. format:@"Must call setExtension() for singular types."];
  1757. }
  1758. if (extensionMap_ == nil) {
  1759. extensionMap_ = [[NSMutableDictionary alloc] init];
  1760. }
  1761. NSMutableArray *list = [extensionMap_ objectForKey:extension];
  1762. if (list == nil) {
  1763. list = [NSMutableArray array];
  1764. [extensionMap_ setObject:list forKey:extension];
  1765. }
  1766. [list addObject:value];
  1767. GPBBecomeVisibleToAutocreator(self);
  1768. }
  1769. - (void)setExtension:(GPBExtensionDescriptor *)extension
  1770. index:(NSUInteger)idx
  1771. value:(id)value {
  1772. CheckExtension(self, extension);
  1773. if (!extension.repeated) {
  1774. [NSException raise:NSInvalidArgumentException
  1775. format:@"Must call setExtension() for singular types."];
  1776. }
  1777. if (extensionMap_ == nil) {
  1778. extensionMap_ = [[NSMutableDictionary alloc] init];
  1779. }
  1780. NSMutableArray *list = [extensionMap_ objectForKey:extension];
  1781. [list replaceObjectAtIndex:idx withObject:value];
  1782. GPBBecomeVisibleToAutocreator(self);
  1783. }
  1784. - (void)clearExtension:(GPBExtensionDescriptor *)extension {
  1785. CheckExtension(self, extension);
  1786. // Only become visible if there was actually a value to clear.
  1787. if ([extensionMap_ objectForKey:extension]) {
  1788. [extensionMap_ removeObjectForKey:extension];
  1789. GPBBecomeVisibleToAutocreator(self);
  1790. }
  1791. }
  1792. #pragma mark - mergeFrom
  1793. - (void)mergeFromData:(NSData *)data
  1794. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry {
  1795. GPBCodedInputStream *input = [[GPBCodedInputStream alloc] initWithData:data];
  1796. [self mergeFromCodedInputStream:input extensionRegistry:extensionRegistry];
  1797. [input checkLastTagWas:0];
  1798. [input release];
  1799. }
  1800. #pragma mark - mergeDelimitedFrom
  1801. - (void)mergeDelimitedFromCodedInputStream:(GPBCodedInputStream *)input
  1802. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry {
  1803. GPBCodedInputStreamState *state = &input->state_;
  1804. if (GPBCodedInputStreamIsAtEnd(state)) {
  1805. return;
  1806. }
  1807. NSData *data = GPBCodedInputStreamReadRetainedBytesNoCopy(state);
  1808. if (data == nil) {
  1809. return;
  1810. }
  1811. [self mergeFromData:data extensionRegistry:extensionRegistry];
  1812. [data release];
  1813. }
  1814. #pragma mark - Parse From Data Support
  1815. + (instancetype)parseFromData:(NSData *)data error:(NSError **)errorPtr {
  1816. return [self parseFromData:data extensionRegistry:nil error:errorPtr];
  1817. }
  1818. + (instancetype)parseFromData:(NSData *)data
  1819. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry
  1820. error:(NSError **)errorPtr {
  1821. return [[[self alloc] initWithData:data
  1822. extensionRegistry:extensionRegistry
  1823. error:errorPtr] autorelease];
  1824. }
  1825. + (instancetype)parseFromCodedInputStream:(GPBCodedInputStream *)input
  1826. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry
  1827. error:(NSError **)errorPtr {
  1828. return
  1829. [[[self alloc] initWithCodedInputStream:input
  1830. extensionRegistry:extensionRegistry
  1831. error:errorPtr] autorelease];
  1832. }
  1833. #pragma mark - Parse Delimited From Data Support
  1834. + (instancetype)parseDelimitedFromCodedInputStream:(GPBCodedInputStream *)input
  1835. extensionRegistry:
  1836. (GPBExtensionRegistry *)extensionRegistry
  1837. error:(NSError **)errorPtr {
  1838. GPBMessage *message = [[[self alloc] init] autorelease];
  1839. @try {
  1840. [message mergeDelimitedFromCodedInputStream:input
  1841. extensionRegistry:extensionRegistry];
  1842. if (errorPtr) {
  1843. *errorPtr = nil;
  1844. }
  1845. }
  1846. @catch (NSException *exception) {
  1847. message = nil;
  1848. if (errorPtr) {
  1849. *errorPtr = ErrorFromException(exception);
  1850. }
  1851. }
  1852. #ifdef DEBUG
  1853. if (message && !message.initialized) {
  1854. message = nil;
  1855. if (errorPtr) {
  1856. *errorPtr = MessageError(GPBMessageErrorCodeMissingRequiredField, nil);
  1857. }
  1858. }
  1859. #endif
  1860. return message;
  1861. }
  1862. #pragma mark - Unknown Field Support
  1863. - (GPBUnknownFieldSet *)unknownFields {
  1864. return unknownFields_;
  1865. }
  1866. - (void)setUnknownFields:(GPBUnknownFieldSet *)unknownFields {
  1867. if (unknownFields != unknownFields_) {
  1868. [unknownFields_ release];
  1869. unknownFields_ = [unknownFields copy];
  1870. GPBBecomeVisibleToAutocreator(self);
  1871. }
  1872. }
  1873. - (void)parseMessageSet:(GPBCodedInputStream *)input
  1874. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry {
  1875. uint32_t typeId = 0;
  1876. NSData *rawBytes = nil;
  1877. GPBExtensionDescriptor *extension = nil;
  1878. GPBCodedInputStreamState *state = &input->state_;
  1879. while (true) {
  1880. uint32_t tag = GPBCodedInputStreamReadTag(state);
  1881. if (tag == 0) {
  1882. break;
  1883. }
  1884. if (tag == GPBWireFormatMessageSetTypeIdTag) {
  1885. typeId = GPBCodedInputStreamReadUInt32(state);
  1886. if (typeId != 0) {
  1887. extension = [extensionRegistry extensionForDescriptor:[self descriptor]
  1888. fieldNumber:typeId];
  1889. }
  1890. } else if (tag == GPBWireFormatMessageSetMessageTag) {
  1891. rawBytes =
  1892. [GPBCodedInputStreamReadRetainedBytesNoCopy(state) autorelease];
  1893. } else {
  1894. if (![input skipField:tag]) {
  1895. break;
  1896. }
  1897. }
  1898. }
  1899. [input checkLastTagWas:GPBWireFormatMessageSetItemEndTag];
  1900. if (rawBytes != nil && typeId != 0) {
  1901. if (extension != nil) {
  1902. GPBCodedInputStream *newInput =
  1903. [[GPBCodedInputStream alloc] initWithData:rawBytes];
  1904. GPBExtensionMergeFromInputStream(extension,
  1905. extension.packable,
  1906. newInput,
  1907. extensionRegistry,
  1908. self);
  1909. [newInput release];
  1910. } else {
  1911. GPBUnknownFieldSet *unknownFields = GetOrMakeUnknownFields(self);
  1912. // rawBytes was created via a NoCopy, so it can be reusing a
  1913. // subrange of another NSData that might go out of scope as things
  1914. // unwind, so a copy is needed to ensure what is saved in the
  1915. // unknown fields stays valid.
  1916. NSData *cloned = [NSData dataWithData:rawBytes];
  1917. [unknownFields mergeMessageSetMessage:typeId data:cloned];
  1918. }
  1919. }
  1920. }
  1921. - (BOOL)parseUnknownField:(GPBCodedInputStream *)input
  1922. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry
  1923. tag:(uint32_t)tag {
  1924. GPBWireFormat wireType = GPBWireFormatGetTagWireType(tag);
  1925. int32_t fieldNumber = GPBWireFormatGetTagFieldNumber(tag);
  1926. GPBDescriptor *descriptor = [self descriptor];
  1927. GPBExtensionDescriptor *extension =
  1928. [extensionRegistry extensionForDescriptor:descriptor
  1929. fieldNumber:fieldNumber];
  1930. if (extension == nil) {
  1931. if (descriptor.wireFormat && GPBWireFormatMessageSetItemTag == tag) {
  1932. [self parseMessageSet:input extensionRegistry:extensionRegistry];
  1933. return YES;
  1934. }
  1935. } else {
  1936. if (extension.wireType == wireType) {
  1937. GPBExtensionMergeFromInputStream(extension,
  1938. extension.packable,
  1939. input,
  1940. extensionRegistry,
  1941. self);
  1942. return YES;
  1943. }
  1944. // Primitive, repeated types can be packed on unpacked on the wire, and are
  1945. // parsed either way.
  1946. if ([extension isRepeated] &&
  1947. !GPBDataTypeIsObject(extension->description_->dataType) &&
  1948. (extension.alternateWireType == wireType)) {
  1949. GPBExtensionMergeFromInputStream(extension,
  1950. !extension.packable,
  1951. input,
  1952. extensionRegistry,
  1953. self);
  1954. return YES;
  1955. }
  1956. }
  1957. if ([GPBUnknownFieldSet isFieldTag:tag]) {
  1958. GPBUnknownFieldSet *unknownFields = GetOrMakeUnknownFields(self);
  1959. return [unknownFields mergeFieldFrom:tag input:input];
  1960. } else {
  1961. return NO;
  1962. }
  1963. }
  1964. - (void)addUnknownMapEntry:(int32_t)fieldNum value:(NSData *)data {
  1965. GPBUnknownFieldSet *unknownFields = GetOrMakeUnknownFields(self);
  1966. [unknownFields addUnknownMapEntry:fieldNum value:data];
  1967. }
  1968. #pragma mark - MergeFromCodedInputStream Support
  1969. static void MergeSingleFieldFromCodedInputStream(
  1970. GPBMessage *self, GPBFieldDescriptor *field, GPBFileSyntax syntax,
  1971. GPBCodedInputStream *input, GPBExtensionRegistry *extensionRegistry) {
  1972. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  1973. switch (fieldDataType) {
  1974. #define CASE_SINGLE_POD(NAME, TYPE, FUNC_TYPE) \
  1975. case GPBDataType##NAME: { \
  1976. TYPE val = GPBCodedInputStreamRead##NAME(&input->state_); \
  1977. GPBSet##FUNC_TYPE##IvarWithFieldPrivate(self, field, val); \
  1978. break; \
  1979. }
  1980. #define CASE_SINGLE_OBJECT(NAME) \
  1981. case GPBDataType##NAME: { \
  1982. id val = GPBCodedInputStreamReadRetained##NAME(&input->state_); \
  1983. GPBSetRetainedObjectIvarWithFieldPrivate(self, field, val); \
  1984. break; \
  1985. }
  1986. CASE_SINGLE_POD(Bool, BOOL, Bool)
  1987. CASE_SINGLE_POD(Fixed32, uint32_t, UInt32)
  1988. CASE_SINGLE_POD(SFixed32, int32_t, Int32)
  1989. CASE_SINGLE_POD(Float, float, Float)
  1990. CASE_SINGLE_POD(Fixed64, uint64_t, UInt64)
  1991. CASE_SINGLE_POD(SFixed64, int64_t, Int64)
  1992. CASE_SINGLE_POD(Double, double, Double)
  1993. CASE_SINGLE_POD(Int32, int32_t, Int32)
  1994. CASE_SINGLE_POD(Int64, int64_t, Int64)
  1995. CASE_SINGLE_POD(SInt32, int32_t, Int32)
  1996. CASE_SINGLE_POD(SInt64, int64_t, Int64)
  1997. CASE_SINGLE_POD(UInt32, uint32_t, UInt32)
  1998. CASE_SINGLE_POD(UInt64, uint64_t, UInt64)
  1999. CASE_SINGLE_OBJECT(Bytes)
  2000. CASE_SINGLE_OBJECT(String)
  2001. #undef CASE_SINGLE_POD
  2002. #undef CASE_SINGLE_OBJECT
  2003. case GPBDataTypeMessage: {
  2004. if (GPBGetHasIvarField(self, field)) {
  2005. // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has
  2006. // check again.
  2007. GPBMessage *message =
  2008. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  2009. [input readMessage:message extensionRegistry:extensionRegistry];
  2010. } else {
  2011. GPBMessage *message = [[field.msgClass alloc] init];
  2012. [input readMessage:message extensionRegistry:extensionRegistry];
  2013. GPBSetRetainedObjectIvarWithFieldPrivate(self, field, message);
  2014. }
  2015. break;
  2016. }
  2017. case GPBDataTypeGroup: {
  2018. if (GPBGetHasIvarField(self, field)) {
  2019. // GPBGetObjectIvarWithFieldNoAutocreate() avoids doing the has
  2020. // check again.
  2021. GPBMessage *message =
  2022. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  2023. [input readGroup:GPBFieldNumber(field)
  2024. message:message
  2025. extensionRegistry:extensionRegistry];
  2026. } else {
  2027. GPBMessage *message = [[field.msgClass alloc] init];
  2028. [input readGroup:GPBFieldNumber(field)
  2029. message:message
  2030. extensionRegistry:extensionRegistry];
  2031. GPBSetRetainedObjectIvarWithFieldPrivate(self, field, message);
  2032. }
  2033. break;
  2034. }
  2035. case GPBDataTypeEnum: {
  2036. int32_t val = GPBCodedInputStreamReadEnum(&input->state_);
  2037. if (GPBHasPreservingUnknownEnumSemantics(syntax) ||
  2038. [field isValidEnumValue:val]) {
  2039. GPBSetInt32IvarWithFieldPrivate(self, field, val);
  2040. } else {
  2041. GPBUnknownFieldSet *unknownFields = GetOrMakeUnknownFields(self);
  2042. [unknownFields mergeVarintField:GPBFieldNumber(field) value:val];
  2043. }
  2044. }
  2045. } // switch
  2046. }
  2047. static void MergeRepeatedPackedFieldFromCodedInputStream(
  2048. GPBMessage *self, GPBFieldDescriptor *field, GPBFileSyntax syntax,
  2049. GPBCodedInputStream *input) {
  2050. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  2051. GPBCodedInputStreamState *state = &input->state_;
  2052. id genericArray = GetOrCreateArrayIvarWithField(self, field);
  2053. int32_t length = GPBCodedInputStreamReadInt32(state);
  2054. size_t limit = GPBCodedInputStreamPushLimit(state, length);
  2055. while (GPBCodedInputStreamBytesUntilLimit(state) > 0) {
  2056. switch (fieldDataType) {
  2057. #define CASE_REPEATED_PACKED_POD(NAME, TYPE, ARRAY_TYPE) \
  2058. case GPBDataType##NAME: { \
  2059. TYPE val = GPBCodedInputStreamRead##NAME(state); \
  2060. [(GPB##ARRAY_TYPE##Array *)genericArray addValue:val]; \
  2061. break; \
  2062. }
  2063. CASE_REPEATED_PACKED_POD(Bool, BOOL, Bool)
  2064. CASE_REPEATED_PACKED_POD(Fixed32, uint32_t, UInt32)
  2065. CASE_REPEATED_PACKED_POD(SFixed32, int32_t, Int32)
  2066. CASE_REPEATED_PACKED_POD(Float, float, Float)
  2067. CASE_REPEATED_PACKED_POD(Fixed64, uint64_t, UInt64)
  2068. CASE_REPEATED_PACKED_POD(SFixed64, int64_t, Int64)
  2069. CASE_REPEATED_PACKED_POD(Double, double, Double)
  2070. CASE_REPEATED_PACKED_POD(Int32, int32_t, Int32)
  2071. CASE_REPEATED_PACKED_POD(Int64, int64_t, Int64)
  2072. CASE_REPEATED_PACKED_POD(SInt32, int32_t, Int32)
  2073. CASE_REPEATED_PACKED_POD(SInt64, int64_t, Int64)
  2074. CASE_REPEATED_PACKED_POD(UInt32, uint32_t, UInt32)
  2075. CASE_REPEATED_PACKED_POD(UInt64, uint64_t, UInt64)
  2076. #undef CASE_REPEATED_PACKED_POD
  2077. case GPBDataTypeBytes:
  2078. case GPBDataTypeString:
  2079. case GPBDataTypeMessage:
  2080. case GPBDataTypeGroup:
  2081. NSCAssert(NO, @"Non primitive types can't be packed");
  2082. break;
  2083. case GPBDataTypeEnum: {
  2084. int32_t val = GPBCodedInputStreamReadEnum(state);
  2085. if (GPBHasPreservingUnknownEnumSemantics(syntax) ||
  2086. [field isValidEnumValue:val]) {
  2087. [(GPBEnumArray*)genericArray addRawValue:val];
  2088. } else {
  2089. GPBUnknownFieldSet *unknownFields = GetOrMakeUnknownFields(self);
  2090. [unknownFields mergeVarintField:GPBFieldNumber(field) value:val];
  2091. }
  2092. break;
  2093. }
  2094. } // switch
  2095. } // while(BytesUntilLimit() > 0)
  2096. GPBCodedInputStreamPopLimit(state, limit);
  2097. }
  2098. static void MergeRepeatedNotPackedFieldFromCodedInputStream(
  2099. GPBMessage *self, GPBFieldDescriptor *field, GPBFileSyntax syntax,
  2100. GPBCodedInputStream *input, GPBExtensionRegistry *extensionRegistry) {
  2101. GPBCodedInputStreamState *state = &input->state_;
  2102. id genericArray = GetOrCreateArrayIvarWithField(self, field);
  2103. switch (GPBGetFieldDataType(field)) {
  2104. #define CASE_REPEATED_NOT_PACKED_POD(NAME, TYPE, ARRAY_TYPE) \
  2105. case GPBDataType##NAME: { \
  2106. TYPE val = GPBCodedInputStreamRead##NAME(state); \
  2107. [(GPB##ARRAY_TYPE##Array *)genericArray addValue:val]; \
  2108. break; \
  2109. }
  2110. #define CASE_REPEATED_NOT_PACKED_OBJECT(NAME) \
  2111. case GPBDataType##NAME: { \
  2112. id val = GPBCodedInputStreamReadRetained##NAME(state); \
  2113. [(NSMutableArray*)genericArray addObject:val]; \
  2114. [val release]; \
  2115. break; \
  2116. }
  2117. CASE_REPEATED_NOT_PACKED_POD(Bool, BOOL, Bool)
  2118. CASE_REPEATED_NOT_PACKED_POD(Fixed32, uint32_t, UInt32)
  2119. CASE_REPEATED_NOT_PACKED_POD(SFixed32, int32_t, Int32)
  2120. CASE_REPEATED_NOT_PACKED_POD(Float, float, Float)
  2121. CASE_REPEATED_NOT_PACKED_POD(Fixed64, uint64_t, UInt64)
  2122. CASE_REPEATED_NOT_PACKED_POD(SFixed64, int64_t, Int64)
  2123. CASE_REPEATED_NOT_PACKED_POD(Double, double, Double)
  2124. CASE_REPEATED_NOT_PACKED_POD(Int32, int32_t, Int32)
  2125. CASE_REPEATED_NOT_PACKED_POD(Int64, int64_t, Int64)
  2126. CASE_REPEATED_NOT_PACKED_POD(SInt32, int32_t, Int32)
  2127. CASE_REPEATED_NOT_PACKED_POD(SInt64, int64_t, Int64)
  2128. CASE_REPEATED_NOT_PACKED_POD(UInt32, uint32_t, UInt32)
  2129. CASE_REPEATED_NOT_PACKED_POD(UInt64, uint64_t, UInt64)
  2130. CASE_REPEATED_NOT_PACKED_OBJECT(Bytes)
  2131. CASE_REPEATED_NOT_PACKED_OBJECT(String)
  2132. #undef CASE_REPEATED_NOT_PACKED_POD
  2133. #undef CASE_NOT_PACKED_OBJECT
  2134. case GPBDataTypeMessage: {
  2135. GPBMessage *message = [[field.msgClass alloc] init];
  2136. [input readMessage:message extensionRegistry:extensionRegistry];
  2137. [(NSMutableArray*)genericArray addObject:message];
  2138. [message release];
  2139. break;
  2140. }
  2141. case GPBDataTypeGroup: {
  2142. GPBMessage *message = [[field.msgClass alloc] init];
  2143. [input readGroup:GPBFieldNumber(field)
  2144. message:message
  2145. extensionRegistry:extensionRegistry];
  2146. [(NSMutableArray*)genericArray addObject:message];
  2147. [message release];
  2148. break;
  2149. }
  2150. case GPBDataTypeEnum: {
  2151. int32_t val = GPBCodedInputStreamReadEnum(state);
  2152. if (GPBHasPreservingUnknownEnumSemantics(syntax) ||
  2153. [field isValidEnumValue:val]) {
  2154. [(GPBEnumArray*)genericArray addRawValue:val];
  2155. } else {
  2156. GPBUnknownFieldSet *unknownFields = GetOrMakeUnknownFields(self);
  2157. [unknownFields mergeVarintField:GPBFieldNumber(field) value:val];
  2158. }
  2159. break;
  2160. }
  2161. } // switch
  2162. }
  2163. - (void)mergeFromCodedInputStream:(GPBCodedInputStream *)input
  2164. extensionRegistry:(GPBExtensionRegistry *)extensionRegistry {
  2165. GPBDescriptor *descriptor = [self descriptor];
  2166. GPBFileSyntax syntax = descriptor.file.syntax;
  2167. GPBCodedInputStreamState *state = &input->state_;
  2168. uint32_t tag = 0;
  2169. NSUInteger startingIndex = 0;
  2170. NSArray *fields = descriptor->fields_;
  2171. NSUInteger numFields = fields.count;
  2172. while (YES) {
  2173. BOOL merged = NO;
  2174. tag = GPBCodedInputStreamReadTag(state);
  2175. if (tag == 0) {
  2176. break; // Reached end.
  2177. }
  2178. for (NSUInteger i = 0; i < numFields; ++i) {
  2179. if (startingIndex >= numFields) startingIndex = 0;
  2180. GPBFieldDescriptor *fieldDescriptor = fields[startingIndex];
  2181. if (GPBFieldTag(fieldDescriptor) == tag) {
  2182. GPBFieldType fieldType = fieldDescriptor.fieldType;
  2183. if (fieldType == GPBFieldTypeSingle) {
  2184. MergeSingleFieldFromCodedInputStream(self, fieldDescriptor, syntax,
  2185. input, extensionRegistry);
  2186. // Well formed protos will only have a single field once, advance
  2187. // the starting index to the next field.
  2188. startingIndex += 1;
  2189. } else if (fieldType == GPBFieldTypeRepeated) {
  2190. if (fieldDescriptor.isPackable) {
  2191. MergeRepeatedPackedFieldFromCodedInputStream(
  2192. self, fieldDescriptor, syntax, input);
  2193. // Well formed protos will only have a repeated field that is
  2194. // packed once, advance the starting index to the next field.
  2195. startingIndex += 1;
  2196. } else {
  2197. MergeRepeatedNotPackedFieldFromCodedInputStream(
  2198. self, fieldDescriptor, syntax, input, extensionRegistry);
  2199. }
  2200. } else { // fieldType == GPBFieldTypeMap
  2201. // GPB*Dictionary or NSDictionary, exact type doesn't matter at this
  2202. // point.
  2203. id map = GetOrCreateMapIvarWithField(self, fieldDescriptor);
  2204. [input readMapEntry:map
  2205. extensionRegistry:extensionRegistry
  2206. field:fieldDescriptor
  2207. parentMessage:self];
  2208. }
  2209. merged = YES;
  2210. break;
  2211. } else {
  2212. startingIndex += 1;
  2213. }
  2214. } // for(i < numFields)
  2215. if (!merged && (tag != 0)) {
  2216. // Primitive, repeated types can be packed on unpacked on the wire, and
  2217. // are parsed either way. The above loop covered tag in the preferred
  2218. // for, so this need to check the alternate form.
  2219. for (NSUInteger i = 0; i < numFields; ++i) {
  2220. if (startingIndex >= numFields) startingIndex = 0;
  2221. GPBFieldDescriptor *fieldDescriptor = fields[startingIndex];
  2222. if ((fieldDescriptor.fieldType == GPBFieldTypeRepeated) &&
  2223. !GPBFieldDataTypeIsObject(fieldDescriptor) &&
  2224. (GPBFieldAlternateTag(fieldDescriptor) == tag)) {
  2225. BOOL alternateIsPacked = !fieldDescriptor.isPackable;
  2226. if (alternateIsPacked) {
  2227. MergeRepeatedPackedFieldFromCodedInputStream(
  2228. self, fieldDescriptor, syntax, input);
  2229. // Well formed protos will only have a repeated field that is
  2230. // packed once, advance the starting index to the next field.
  2231. startingIndex += 1;
  2232. } else {
  2233. MergeRepeatedNotPackedFieldFromCodedInputStream(
  2234. self, fieldDescriptor, syntax, input, extensionRegistry);
  2235. }
  2236. merged = YES;
  2237. break;
  2238. } else {
  2239. startingIndex += 1;
  2240. }
  2241. }
  2242. }
  2243. if (!merged) {
  2244. if (tag == 0) {
  2245. // zero signals EOF / limit reached
  2246. return;
  2247. } else {
  2248. if (![self parseUnknownField:input
  2249. extensionRegistry:extensionRegistry
  2250. tag:tag]) {
  2251. // it's an endgroup tag
  2252. return;
  2253. }
  2254. }
  2255. } // if(!merged)
  2256. } // while(YES)
  2257. }
  2258. #pragma mark - MergeFrom Support
  2259. - (void)mergeFrom:(GPBMessage *)other {
  2260. Class selfClass = [self class];
  2261. Class otherClass = [other class];
  2262. if (!([selfClass isSubclassOfClass:otherClass] ||
  2263. [otherClass isSubclassOfClass:selfClass])) {
  2264. [NSException raise:NSInvalidArgumentException
  2265. format:@"Classes must match %@ != %@", selfClass, otherClass];
  2266. }
  2267. // We assume something will be done and become visible.
  2268. GPBBecomeVisibleToAutocreator(self);
  2269. GPBDescriptor *descriptor = [[self class] descriptor];
  2270. for (GPBFieldDescriptor *field in descriptor->fields_) {
  2271. GPBFieldType fieldType = field.fieldType;
  2272. if (fieldType == GPBFieldTypeSingle) {
  2273. int32_t hasIndex = GPBFieldHasIndex(field);
  2274. uint32_t fieldNumber = GPBFieldNumber(field);
  2275. if (!GPBGetHasIvar(other, hasIndex, fieldNumber)) {
  2276. // Other doesn't have the field set, on to the next.
  2277. continue;
  2278. }
  2279. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  2280. switch (fieldDataType) {
  2281. case GPBDataTypeBool:
  2282. GPBSetBoolIvarWithFieldPrivate(
  2283. self, field, GPBGetMessageBoolField(other, field));
  2284. break;
  2285. case GPBDataTypeSFixed32:
  2286. case GPBDataTypeEnum:
  2287. case GPBDataTypeInt32:
  2288. case GPBDataTypeSInt32:
  2289. GPBSetInt32IvarWithFieldPrivate(
  2290. self, field, GPBGetMessageInt32Field(other, field));
  2291. break;
  2292. case GPBDataTypeFixed32:
  2293. case GPBDataTypeUInt32:
  2294. GPBSetUInt32IvarWithFieldPrivate(
  2295. self, field, GPBGetMessageUInt32Field(other, field));
  2296. break;
  2297. case GPBDataTypeSFixed64:
  2298. case GPBDataTypeInt64:
  2299. case GPBDataTypeSInt64:
  2300. GPBSetInt64IvarWithFieldPrivate(
  2301. self, field, GPBGetMessageInt64Field(other, field));
  2302. break;
  2303. case GPBDataTypeFixed64:
  2304. case GPBDataTypeUInt64:
  2305. GPBSetUInt64IvarWithFieldPrivate(
  2306. self, field, GPBGetMessageUInt64Field(other, field));
  2307. break;
  2308. case GPBDataTypeFloat:
  2309. GPBSetFloatIvarWithFieldPrivate(
  2310. self, field, GPBGetMessageFloatField(other, field));
  2311. break;
  2312. case GPBDataTypeDouble:
  2313. GPBSetDoubleIvarWithFieldPrivate(
  2314. self, field, GPBGetMessageDoubleField(other, field));
  2315. break;
  2316. case GPBDataTypeBytes:
  2317. case GPBDataTypeString: {
  2318. id otherVal = GPBGetObjectIvarWithFieldNoAutocreate(other, field);
  2319. GPBSetObjectIvarWithFieldPrivate(self, field, otherVal);
  2320. break;
  2321. }
  2322. case GPBDataTypeMessage:
  2323. case GPBDataTypeGroup: {
  2324. id otherVal = GPBGetObjectIvarWithFieldNoAutocreate(other, field);
  2325. if (GPBGetHasIvar(self, hasIndex, fieldNumber)) {
  2326. GPBMessage *message =
  2327. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  2328. [message mergeFrom:otherVal];
  2329. } else {
  2330. GPBMessage *message = [otherVal copy];
  2331. GPBSetRetainedObjectIvarWithFieldPrivate(self, field, message);
  2332. }
  2333. break;
  2334. }
  2335. } // switch()
  2336. } else if (fieldType == GPBFieldTypeRepeated) {
  2337. // In the case of a list, they need to be appended, and there is no
  2338. // _hasIvar to worry about setting.
  2339. id otherArray =
  2340. GPBGetObjectIvarWithFieldNoAutocreate(other, field);
  2341. if (otherArray) {
  2342. GPBDataType fieldDataType = field->description_->dataType;
  2343. if (GPBDataTypeIsObject(fieldDataType)) {
  2344. NSMutableArray *resultArray =
  2345. GetOrCreateArrayIvarWithField(self, field);
  2346. [resultArray addObjectsFromArray:otherArray];
  2347. } else if (fieldDataType == GPBDataTypeEnum) {
  2348. GPBEnumArray *resultArray =
  2349. GetOrCreateArrayIvarWithField(self, field);
  2350. [resultArray addRawValuesFromArray:otherArray];
  2351. } else {
  2352. // The array type doesn't matter, that all implement
  2353. // -addValuesFromArray:.
  2354. GPBInt32Array *resultArray =
  2355. GetOrCreateArrayIvarWithField(self, field);
  2356. [resultArray addValuesFromArray:otherArray];
  2357. }
  2358. }
  2359. } else { // fieldType = GPBFieldTypeMap
  2360. // In the case of a map, they need to be merged, and there is no
  2361. // _hasIvar to worry about setting.
  2362. id otherDict = GPBGetObjectIvarWithFieldNoAutocreate(other, field);
  2363. if (otherDict) {
  2364. GPBDataType keyDataType = field.mapKeyDataType;
  2365. GPBDataType valueDataType = field->description_->dataType;
  2366. if (GPBDataTypeIsObject(keyDataType) &&
  2367. GPBDataTypeIsObject(valueDataType)) {
  2368. NSMutableDictionary *resultDict =
  2369. GetOrCreateMapIvarWithField(self, field);
  2370. [resultDict addEntriesFromDictionary:otherDict];
  2371. } else if (valueDataType == GPBDataTypeEnum) {
  2372. // The exact type doesn't matter, just need to know it is a
  2373. // GPB*EnumDictionary.
  2374. GPBInt32EnumDictionary *resultDict =
  2375. GetOrCreateMapIvarWithField(self, field);
  2376. [resultDict addRawEntriesFromDictionary:otherDict];
  2377. } else {
  2378. // The exact type doesn't matter, they all implement
  2379. // -addEntriesFromDictionary:.
  2380. GPBInt32Int32Dictionary *resultDict =
  2381. GetOrCreateMapIvarWithField(self, field);
  2382. [resultDict addEntriesFromDictionary:otherDict];
  2383. }
  2384. }
  2385. } // if (fieldType)..else if...else
  2386. } // for(fields)
  2387. // Unknown fields.
  2388. if (!unknownFields_) {
  2389. [self setUnknownFields:other.unknownFields];
  2390. } else {
  2391. [unknownFields_ mergeUnknownFields:other.unknownFields];
  2392. }
  2393. // Extensions
  2394. if (other->extensionMap_.count == 0) {
  2395. return;
  2396. }
  2397. if (extensionMap_ == nil) {
  2398. extensionMap_ =
  2399. CloneExtensionMap(other->extensionMap_, NSZoneFromPointer(self));
  2400. } else {
  2401. for (GPBExtensionDescriptor *extension in other->extensionMap_) {
  2402. id otherValue = [other->extensionMap_ objectForKey:extension];
  2403. id value = [extensionMap_ objectForKey:extension];
  2404. BOOL isMessageExtension = GPBExtensionIsMessage(extension);
  2405. if (extension.repeated) {
  2406. NSMutableArray *list = value;
  2407. if (list == nil) {
  2408. list = [[NSMutableArray alloc] init];
  2409. [extensionMap_ setObject:list forKey:extension];
  2410. [list release];
  2411. }
  2412. if (isMessageExtension) {
  2413. for (GPBMessage *otherListValue in otherValue) {
  2414. GPBMessage *copiedValue = [otherListValue copy];
  2415. [list addObject:copiedValue];
  2416. [copiedValue release];
  2417. }
  2418. } else {
  2419. [list addObjectsFromArray:otherValue];
  2420. }
  2421. } else {
  2422. if (isMessageExtension) {
  2423. if (value) {
  2424. [(GPBMessage *)value mergeFrom:(GPBMessage *)otherValue];
  2425. } else {
  2426. GPBMessage *copiedValue = [otherValue copy];
  2427. [extensionMap_ setObject:copiedValue forKey:extension];
  2428. [copiedValue release];
  2429. }
  2430. } else {
  2431. [extensionMap_ setObject:otherValue forKey:extension];
  2432. }
  2433. }
  2434. if (isMessageExtension && !extension.isRepeated) {
  2435. GPBMessage *autocreatedValue =
  2436. [[autocreatedExtensionMap_ objectForKey:extension] retain];
  2437. // Must remove from the map before calling GPBClearMessageAutocreator()
  2438. // so that GPBClearMessageAutocreator() knows its safe to clear.
  2439. [autocreatedExtensionMap_ removeObjectForKey:extension];
  2440. GPBClearMessageAutocreator(autocreatedValue);
  2441. [autocreatedValue release];
  2442. }
  2443. }
  2444. }
  2445. }
  2446. #pragma mark - isEqual: & hash Support
  2447. - (BOOL)isEqual:(id)other {
  2448. if (other == self) {
  2449. return YES;
  2450. }
  2451. if (![other isKindOfClass:[GPBMessage class]]) {
  2452. return NO;
  2453. }
  2454. GPBMessage *otherMsg = other;
  2455. GPBDescriptor *descriptor = [[self class] descriptor];
  2456. if ([[otherMsg class] descriptor] != descriptor) {
  2457. return NO;
  2458. }
  2459. uint8_t *selfStorage = (uint8_t *)messageStorage_;
  2460. uint8_t *otherStorage = (uint8_t *)otherMsg->messageStorage_;
  2461. for (GPBFieldDescriptor *field in descriptor->fields_) {
  2462. if (GPBFieldIsMapOrArray(field)) {
  2463. // In the case of a list or map, there is no _hasIvar to worry about.
  2464. // NOTE: These are NSArray/GPB*Array or NSDictionary/GPB*Dictionary, but
  2465. // the type doesn't really matter as the objects all support -count and
  2466. // -isEqual:.
  2467. NSArray *resultMapOrArray =
  2468. GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  2469. NSArray *otherMapOrArray =
  2470. GPBGetObjectIvarWithFieldNoAutocreate(other, field);
  2471. // nil and empty are equal
  2472. if (resultMapOrArray.count != 0 || otherMapOrArray.count != 0) {
  2473. if (![resultMapOrArray isEqual:otherMapOrArray]) {
  2474. return NO;
  2475. }
  2476. }
  2477. } else { // Single field
  2478. int32_t hasIndex = GPBFieldHasIndex(field);
  2479. uint32_t fieldNum = GPBFieldNumber(field);
  2480. BOOL selfHas = GPBGetHasIvar(self, hasIndex, fieldNum);
  2481. BOOL otherHas = GPBGetHasIvar(other, hasIndex, fieldNum);
  2482. if (selfHas != otherHas) {
  2483. return NO; // Differing has values, not equal.
  2484. }
  2485. if (!selfHas) {
  2486. // Same has values, was no, nothing else to check for this field.
  2487. continue;
  2488. }
  2489. // Now compare the values.
  2490. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  2491. size_t fieldOffset = field->description_->offset;
  2492. switch (fieldDataType) {
  2493. case GPBDataTypeBool: {
  2494. // Bools are stored in has_bits to avoid needing explicit space in
  2495. // the storage structure.
  2496. // (the field number passed to the HasIvar helper doesn't really
  2497. // matter since the offset is never negative)
  2498. BOOL selfValue = GPBGetHasIvar(self, (int32_t)(fieldOffset), 0);
  2499. BOOL otherValue = GPBGetHasIvar(other, (int32_t)(fieldOffset), 0);
  2500. if (selfValue != otherValue) {
  2501. return NO;
  2502. }
  2503. break;
  2504. }
  2505. case GPBDataTypeSFixed32:
  2506. case GPBDataTypeInt32:
  2507. case GPBDataTypeSInt32:
  2508. case GPBDataTypeEnum:
  2509. case GPBDataTypeFixed32:
  2510. case GPBDataTypeUInt32:
  2511. case GPBDataTypeFloat: {
  2512. GPBInternalCompileAssert(sizeof(float) == sizeof(uint32_t), float_not_32_bits);
  2513. // These are all 32bit, signed/unsigned doesn't matter for equality.
  2514. uint32_t *selfValPtr = (uint32_t *)&selfStorage[fieldOffset];
  2515. uint32_t *otherValPtr = (uint32_t *)&otherStorage[fieldOffset];
  2516. if (*selfValPtr != *otherValPtr) {
  2517. return NO;
  2518. }
  2519. break;
  2520. }
  2521. case GPBDataTypeSFixed64:
  2522. case GPBDataTypeInt64:
  2523. case GPBDataTypeSInt64:
  2524. case GPBDataTypeFixed64:
  2525. case GPBDataTypeUInt64:
  2526. case GPBDataTypeDouble: {
  2527. GPBInternalCompileAssert(sizeof(double) == sizeof(uint64_t), double_not_64_bits);
  2528. // These are all 64bit, signed/unsigned doesn't matter for equality.
  2529. uint64_t *selfValPtr = (uint64_t *)&selfStorage[fieldOffset];
  2530. uint64_t *otherValPtr = (uint64_t *)&otherStorage[fieldOffset];
  2531. if (*selfValPtr != *otherValPtr) {
  2532. return NO;
  2533. }
  2534. break;
  2535. }
  2536. case GPBDataTypeBytes:
  2537. case GPBDataTypeString:
  2538. case GPBDataTypeMessage:
  2539. case GPBDataTypeGroup: {
  2540. // Type doesn't matter here, they all implement -isEqual:.
  2541. id *selfValPtr = (id *)&selfStorage[fieldOffset];
  2542. id *otherValPtr = (id *)&otherStorage[fieldOffset];
  2543. if (![*selfValPtr isEqual:*otherValPtr]) {
  2544. return NO;
  2545. }
  2546. break;
  2547. }
  2548. } // switch()
  2549. } // if(mapOrArray)...else
  2550. } // for(fields)
  2551. // nil and empty are equal
  2552. if (extensionMap_.count != 0 || otherMsg->extensionMap_.count != 0) {
  2553. if (![extensionMap_ isEqual:otherMsg->extensionMap_]) {
  2554. return NO;
  2555. }
  2556. }
  2557. // nil and empty are equal
  2558. GPBUnknownFieldSet *otherUnknowns = otherMsg->unknownFields_;
  2559. if ([unknownFields_ countOfFields] != 0 ||
  2560. [otherUnknowns countOfFields] != 0) {
  2561. if (![unknownFields_ isEqual:otherUnknowns]) {
  2562. return NO;
  2563. }
  2564. }
  2565. return YES;
  2566. }
  2567. // It is very difficult to implement a generic hash for ProtoBuf messages that
  2568. // will perform well. If you need hashing on your ProtoBufs (eg you are using
  2569. // them as dictionary keys) you will probably want to implement a ProtoBuf
  2570. // message specific hash as a category on your protobuf class. Do not make it a
  2571. // category on GPBMessage as you will conflict with this hash, and will possibly
  2572. // override hash for all generated protobufs. A good implementation of hash will
  2573. // be really fast, so we would recommend only hashing protobufs that have an
  2574. // identifier field of some kind that you can easily hash. If you implement
  2575. // hash, we would strongly recommend overriding isEqual: in your category as
  2576. // well, as the default implementation of isEqual: is extremely slow, and may
  2577. // drastically affect performance in large sets.
  2578. - (NSUInteger)hash {
  2579. GPBDescriptor *descriptor = [[self class] descriptor];
  2580. const NSUInteger prime = 19;
  2581. uint8_t *storage = (uint8_t *)messageStorage_;
  2582. // Start with the descriptor and then mix it with some instance info.
  2583. // Hopefully that will give a spread based on classes and what fields are set.
  2584. NSUInteger result = (NSUInteger)descriptor;
  2585. for (GPBFieldDescriptor *field in descriptor->fields_) {
  2586. if (GPBFieldIsMapOrArray(field)) {
  2587. // Exact type doesn't matter, just check if there are any elements.
  2588. NSArray *mapOrArray = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  2589. NSUInteger count = mapOrArray.count;
  2590. if (count) {
  2591. // NSArray/NSDictionary use count, use the field number and the count.
  2592. result = prime * result + GPBFieldNumber(field);
  2593. result = prime * result + count;
  2594. }
  2595. } else if (GPBGetHasIvarField(self, field)) {
  2596. // Just using the field number seemed simple/fast, but then a small
  2597. // message class where all the same fields are always set (to different
  2598. // things would end up all with the same hash, so pull in some data).
  2599. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  2600. size_t fieldOffset = field->description_->offset;
  2601. switch (fieldDataType) {
  2602. case GPBDataTypeBool: {
  2603. // Bools are stored in has_bits to avoid needing explicit space in
  2604. // the storage structure.
  2605. // (the field number passed to the HasIvar helper doesn't really
  2606. // matter since the offset is never negative)
  2607. BOOL value = GPBGetHasIvar(self, (int32_t)(fieldOffset), 0);
  2608. result = prime * result + value;
  2609. break;
  2610. }
  2611. case GPBDataTypeSFixed32:
  2612. case GPBDataTypeInt32:
  2613. case GPBDataTypeSInt32:
  2614. case GPBDataTypeEnum:
  2615. case GPBDataTypeFixed32:
  2616. case GPBDataTypeUInt32:
  2617. case GPBDataTypeFloat: {
  2618. GPBInternalCompileAssert(sizeof(float) == sizeof(uint32_t), float_not_32_bits);
  2619. // These are all 32bit, just mix it in.
  2620. uint32_t *valPtr = (uint32_t *)&storage[fieldOffset];
  2621. result = prime * result + *valPtr;
  2622. break;
  2623. }
  2624. case GPBDataTypeSFixed64:
  2625. case GPBDataTypeInt64:
  2626. case GPBDataTypeSInt64:
  2627. case GPBDataTypeFixed64:
  2628. case GPBDataTypeUInt64:
  2629. case GPBDataTypeDouble: {
  2630. GPBInternalCompileAssert(sizeof(double) == sizeof(uint64_t), double_not_64_bits);
  2631. // These are all 64bit, just mix what fits into an NSUInteger in.
  2632. uint64_t *valPtr = (uint64_t *)&storage[fieldOffset];
  2633. result = prime * result + (NSUInteger)(*valPtr);
  2634. break;
  2635. }
  2636. case GPBDataTypeBytes:
  2637. case GPBDataTypeString: {
  2638. // Type doesn't matter here, they both implement -hash:.
  2639. id *valPtr = (id *)&storage[fieldOffset];
  2640. result = prime * result + [*valPtr hash];
  2641. break;
  2642. }
  2643. case GPBDataTypeMessage:
  2644. case GPBDataTypeGroup: {
  2645. GPBMessage **valPtr = (GPBMessage **)&storage[fieldOffset];
  2646. // Could call -hash on the sub message, but that could recurse pretty
  2647. // deep; follow the lead of NSArray/NSDictionary and don't really
  2648. // recurse for hash, instead use the field number and the descriptor
  2649. // of the sub message. Yes, this could suck for a bunch of messages
  2650. // where they all only differ in the sub messages, but if you are
  2651. // using a message with sub messages for something that needs -hash,
  2652. // odds are you are also copying them as keys, and that deep copy
  2653. // will also suck.
  2654. result = prime * result + GPBFieldNumber(field);
  2655. result = prime * result + (NSUInteger)[[*valPtr class] descriptor];
  2656. break;
  2657. }
  2658. } // switch()
  2659. }
  2660. }
  2661. // Unknowns and extensions are not included.
  2662. return result;
  2663. }
  2664. #pragma mark - Description Support
  2665. - (NSString *)description {
  2666. NSString *textFormat = GPBTextFormatForMessage(self, @" ");
  2667. NSString *description = [NSString
  2668. stringWithFormat:@"<%@ %p>: {\n%@}", [self class], self, textFormat];
  2669. return description;
  2670. }
  2671. #if defined(DEBUG) && DEBUG
  2672. // Xcode 5.1 added support for custom quick look info.
  2673. // https://developer.apple.com/library/ios/documentation/IDEs/Conceptual/CustomClassDisplay_in_QuickLook/CH01-quick_look_for_custom_objects/CH01-quick_look_for_custom_objects.html#//apple_ref/doc/uid/TP40014001-CH2-SW1
  2674. - (id)debugQuickLookObject {
  2675. return GPBTextFormatForMessage(self, nil);
  2676. }
  2677. #endif // DEBUG
  2678. #pragma mark - SerializedSize
  2679. - (size_t)serializedSize {
  2680. GPBDescriptor *descriptor = [[self class] descriptor];
  2681. size_t result = 0;
  2682. // Has check is done explicitly, so GPBGetObjectIvarWithFieldNoAutocreate()
  2683. // avoids doing the has check again.
  2684. // Fields.
  2685. for (GPBFieldDescriptor *fieldDescriptor in descriptor->fields_) {
  2686. GPBFieldType fieldType = fieldDescriptor.fieldType;
  2687. GPBDataType fieldDataType = GPBGetFieldDataType(fieldDescriptor);
  2688. // Single Fields
  2689. if (fieldType == GPBFieldTypeSingle) {
  2690. BOOL selfHas = GPBGetHasIvarField(self, fieldDescriptor);
  2691. if (!selfHas) {
  2692. continue; // Nothing to do.
  2693. }
  2694. uint32_t fieldNumber = GPBFieldNumber(fieldDescriptor);
  2695. switch (fieldDataType) {
  2696. #define CASE_SINGLE_POD(NAME, TYPE, FUNC_TYPE) \
  2697. case GPBDataType##NAME: { \
  2698. TYPE fieldVal = GPBGetMessage##FUNC_TYPE##Field(self, fieldDescriptor); \
  2699. result += GPBCompute##NAME##Size(fieldNumber, fieldVal); \
  2700. break; \
  2701. }
  2702. #define CASE_SINGLE_OBJECT(NAME) \
  2703. case GPBDataType##NAME: { \
  2704. id fieldVal = GPBGetObjectIvarWithFieldNoAutocreate(self, fieldDescriptor); \
  2705. result += GPBCompute##NAME##Size(fieldNumber, fieldVal); \
  2706. break; \
  2707. }
  2708. CASE_SINGLE_POD(Bool, BOOL, Bool)
  2709. CASE_SINGLE_POD(Fixed32, uint32_t, UInt32)
  2710. CASE_SINGLE_POD(SFixed32, int32_t, Int32)
  2711. CASE_SINGLE_POD(Float, float, Float)
  2712. CASE_SINGLE_POD(Fixed64, uint64_t, UInt64)
  2713. CASE_SINGLE_POD(SFixed64, int64_t, Int64)
  2714. CASE_SINGLE_POD(Double, double, Double)
  2715. CASE_SINGLE_POD(Int32, int32_t, Int32)
  2716. CASE_SINGLE_POD(Int64, int64_t, Int64)
  2717. CASE_SINGLE_POD(SInt32, int32_t, Int32)
  2718. CASE_SINGLE_POD(SInt64, int64_t, Int64)
  2719. CASE_SINGLE_POD(UInt32, uint32_t, UInt32)
  2720. CASE_SINGLE_POD(UInt64, uint64_t, UInt64)
  2721. CASE_SINGLE_OBJECT(Bytes)
  2722. CASE_SINGLE_OBJECT(String)
  2723. CASE_SINGLE_OBJECT(Message)
  2724. CASE_SINGLE_OBJECT(Group)
  2725. CASE_SINGLE_POD(Enum, int32_t, Int32)
  2726. #undef CASE_SINGLE_POD
  2727. #undef CASE_SINGLE_OBJECT
  2728. }
  2729. // Repeated Fields
  2730. } else if (fieldType == GPBFieldTypeRepeated) {
  2731. id genericArray =
  2732. GPBGetObjectIvarWithFieldNoAutocreate(self, fieldDescriptor);
  2733. NSUInteger count = [genericArray count];
  2734. if (count == 0) {
  2735. continue; // Nothing to add.
  2736. }
  2737. __block size_t dataSize = 0;
  2738. switch (fieldDataType) {
  2739. #define CASE_REPEATED_POD(NAME, TYPE, ARRAY_TYPE) \
  2740. CASE_REPEATED_POD_EXTRA(NAME, TYPE, ARRAY_TYPE, )
  2741. #define CASE_REPEATED_POD_EXTRA(NAME, TYPE, ARRAY_TYPE, ARRAY_ACCESSOR_NAME) \
  2742. case GPBDataType##NAME: { \
  2743. GPB##ARRAY_TYPE##Array *array = genericArray; \
  2744. [array enumerate##ARRAY_ACCESSOR_NAME##ValuesWithBlock:^(TYPE value, NSUInteger idx, BOOL *stop) { \
  2745. _Pragma("unused(idx, stop)"); \
  2746. dataSize += GPBCompute##NAME##SizeNoTag(value); \
  2747. }]; \
  2748. break; \
  2749. }
  2750. #define CASE_REPEATED_OBJECT(NAME) \
  2751. case GPBDataType##NAME: { \
  2752. for (id value in genericArray) { \
  2753. dataSize += GPBCompute##NAME##SizeNoTag(value); \
  2754. } \
  2755. break; \
  2756. }
  2757. CASE_REPEATED_POD(Bool, BOOL, Bool)
  2758. CASE_REPEATED_POD(Fixed32, uint32_t, UInt32)
  2759. CASE_REPEATED_POD(SFixed32, int32_t, Int32)
  2760. CASE_REPEATED_POD(Float, float, Float)
  2761. CASE_REPEATED_POD(Fixed64, uint64_t, UInt64)
  2762. CASE_REPEATED_POD(SFixed64, int64_t, Int64)
  2763. CASE_REPEATED_POD(Double, double, Double)
  2764. CASE_REPEATED_POD(Int32, int32_t, Int32)
  2765. CASE_REPEATED_POD(Int64, int64_t, Int64)
  2766. CASE_REPEATED_POD(SInt32, int32_t, Int32)
  2767. CASE_REPEATED_POD(SInt64, int64_t, Int64)
  2768. CASE_REPEATED_POD(UInt32, uint32_t, UInt32)
  2769. CASE_REPEATED_POD(UInt64, uint64_t, UInt64)
  2770. CASE_REPEATED_OBJECT(Bytes)
  2771. CASE_REPEATED_OBJECT(String)
  2772. CASE_REPEATED_OBJECT(Message)
  2773. CASE_REPEATED_OBJECT(Group)
  2774. CASE_REPEATED_POD_EXTRA(Enum, int32_t, Enum, Raw)
  2775. #undef CASE_REPEATED_POD
  2776. #undef CASE_REPEATED_POD_EXTRA
  2777. #undef CASE_REPEATED_OBJECT
  2778. } // switch
  2779. result += dataSize;
  2780. size_t tagSize = GPBComputeTagSize(GPBFieldNumber(fieldDescriptor));
  2781. if (fieldDataType == GPBDataTypeGroup) {
  2782. // Groups have both a start and an end tag.
  2783. tagSize *= 2;
  2784. }
  2785. if (fieldDescriptor.isPackable) {
  2786. result += tagSize;
  2787. result += GPBComputeSizeTSizeAsInt32NoTag(dataSize);
  2788. } else {
  2789. result += count * tagSize;
  2790. }
  2791. // Map<> Fields
  2792. } else { // fieldType == GPBFieldTypeMap
  2793. if (GPBDataTypeIsObject(fieldDataType) &&
  2794. (fieldDescriptor.mapKeyDataType == GPBDataTypeString)) {
  2795. // If key type was string, then the map is an NSDictionary.
  2796. NSDictionary *map =
  2797. GPBGetObjectIvarWithFieldNoAutocreate(self, fieldDescriptor);
  2798. if (map) {
  2799. result += GPBDictionaryComputeSizeInternalHelper(map, fieldDescriptor);
  2800. }
  2801. } else {
  2802. // Type will be GPB*GroupDictionary, exact type doesn't matter.
  2803. GPBInt32Int32Dictionary *map =
  2804. GPBGetObjectIvarWithFieldNoAutocreate(self, fieldDescriptor);
  2805. result += [map computeSerializedSizeAsField:fieldDescriptor];
  2806. }
  2807. }
  2808. } // for(fields)
  2809. // Add any unknown fields.
  2810. if (descriptor.wireFormat) {
  2811. result += [unknownFields_ serializedSizeAsMessageSet];
  2812. } else {
  2813. result += [unknownFields_ serializedSize];
  2814. }
  2815. // Add any extensions.
  2816. for (GPBExtensionDescriptor *extension in extensionMap_) {
  2817. id value = [extensionMap_ objectForKey:extension];
  2818. result += GPBComputeExtensionSerializedSizeIncludingTag(extension, value);
  2819. }
  2820. return result;
  2821. }
  2822. #pragma mark - Resolve Methods Support
  2823. typedef struct ResolveIvarAccessorMethodResult {
  2824. IMP impToAdd;
  2825. SEL encodingSelector;
  2826. } ResolveIvarAccessorMethodResult;
  2827. // |field| can be __unsafe_unretained because they are created at startup
  2828. // and are essentially global. No need to pay for retain/release when
  2829. // they are captured in blocks.
  2830. static void ResolveIvarGet(__unsafe_unretained GPBFieldDescriptor *field,
  2831. ResolveIvarAccessorMethodResult *result) {
  2832. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  2833. switch (fieldDataType) {
  2834. #define CASE_GET(NAME, TYPE, TRUE_NAME) \
  2835. case GPBDataType##NAME: { \
  2836. result->impToAdd = imp_implementationWithBlock(^(id obj) { \
  2837. return GPBGetMessage##TRUE_NAME##Field(obj, field); \
  2838. }); \
  2839. result->encodingSelector = @selector(get##NAME); \
  2840. break; \
  2841. }
  2842. #define CASE_GET_OBJECT(NAME, TYPE, TRUE_NAME) \
  2843. case GPBDataType##NAME: { \
  2844. result->impToAdd = imp_implementationWithBlock(^(id obj) { \
  2845. return GPBGetObjectIvarWithField(obj, field); \
  2846. }); \
  2847. result->encodingSelector = @selector(get##NAME); \
  2848. break; \
  2849. }
  2850. CASE_GET(Bool, BOOL, Bool)
  2851. CASE_GET(Fixed32, uint32_t, UInt32)
  2852. CASE_GET(SFixed32, int32_t, Int32)
  2853. CASE_GET(Float, float, Float)
  2854. CASE_GET(Fixed64, uint64_t, UInt64)
  2855. CASE_GET(SFixed64, int64_t, Int64)
  2856. CASE_GET(Double, double, Double)
  2857. CASE_GET(Int32, int32_t, Int32)
  2858. CASE_GET(Int64, int64_t, Int64)
  2859. CASE_GET(SInt32, int32_t, Int32)
  2860. CASE_GET(SInt64, int64_t, Int64)
  2861. CASE_GET(UInt32, uint32_t, UInt32)
  2862. CASE_GET(UInt64, uint64_t, UInt64)
  2863. CASE_GET_OBJECT(Bytes, id, Object)
  2864. CASE_GET_OBJECT(String, id, Object)
  2865. CASE_GET_OBJECT(Message, id, Object)
  2866. CASE_GET_OBJECT(Group, id, Object)
  2867. CASE_GET(Enum, int32_t, Enum)
  2868. #undef CASE_GET
  2869. }
  2870. }
  2871. // See comment about __unsafe_unretained on ResolveIvarGet.
  2872. static void ResolveIvarSet(__unsafe_unretained GPBFieldDescriptor *field,
  2873. ResolveIvarAccessorMethodResult *result) {
  2874. GPBDataType fieldDataType = GPBGetFieldDataType(field);
  2875. switch (fieldDataType) {
  2876. #define CASE_SET(NAME, TYPE, TRUE_NAME) \
  2877. case GPBDataType##NAME: { \
  2878. result->impToAdd = imp_implementationWithBlock(^(id obj, TYPE value) { \
  2879. return GPBSet##TRUE_NAME##IvarWithFieldPrivate(obj, field, value); \
  2880. }); \
  2881. result->encodingSelector = @selector(set##NAME:); \
  2882. break; \
  2883. }
  2884. #define CASE_SET_COPY(NAME) \
  2885. case GPBDataType##NAME: { \
  2886. result->impToAdd = imp_implementationWithBlock(^(id obj, id value) { \
  2887. return GPBSetRetainedObjectIvarWithFieldPrivate(obj, field, [value copy]); \
  2888. }); \
  2889. result->encodingSelector = @selector(set##NAME:); \
  2890. break; \
  2891. }
  2892. CASE_SET(Bool, BOOL, Bool)
  2893. CASE_SET(Fixed32, uint32_t, UInt32)
  2894. CASE_SET(SFixed32, int32_t, Int32)
  2895. CASE_SET(Float, float, Float)
  2896. CASE_SET(Fixed64, uint64_t, UInt64)
  2897. CASE_SET(SFixed64, int64_t, Int64)
  2898. CASE_SET(Double, double, Double)
  2899. CASE_SET(Int32, int32_t, Int32)
  2900. CASE_SET(Int64, int64_t, Int64)
  2901. CASE_SET(SInt32, int32_t, Int32)
  2902. CASE_SET(SInt64, int64_t, Int64)
  2903. CASE_SET(UInt32, uint32_t, UInt32)
  2904. CASE_SET(UInt64, uint64_t, UInt64)
  2905. CASE_SET_COPY(Bytes)
  2906. CASE_SET_COPY(String)
  2907. CASE_SET(Message, id, Object)
  2908. CASE_SET(Group, id, Object)
  2909. CASE_SET(Enum, int32_t, Enum)
  2910. #undef CASE_SET
  2911. }
  2912. }
  2913. + (BOOL)resolveInstanceMethod:(SEL)sel {
  2914. const GPBDescriptor *descriptor = [self descriptor];
  2915. if (!descriptor) {
  2916. return [super resolveInstanceMethod:sel];
  2917. }
  2918. // NOTE: hasOrCountSel_/setHasSel_ will be NULL if the field for the given
  2919. // message should not have has support (done in GPBDescriptor.m), so there is
  2920. // no need for checks here to see if has*/setHas* are allowed.
  2921. ResolveIvarAccessorMethodResult result = {NULL, NULL};
  2922. // See comment about __unsafe_unretained on ResolveIvarGet.
  2923. for (__unsafe_unretained GPBFieldDescriptor *field in descriptor->fields_) {
  2924. BOOL isMapOrArray = GPBFieldIsMapOrArray(field);
  2925. if (!isMapOrArray) {
  2926. // Single fields.
  2927. if (sel == field->getSel_) {
  2928. ResolveIvarGet(field, &result);
  2929. break;
  2930. } else if (sel == field->setSel_) {
  2931. ResolveIvarSet(field, &result);
  2932. break;
  2933. } else if (sel == field->hasOrCountSel_) {
  2934. int32_t index = GPBFieldHasIndex(field);
  2935. uint32_t fieldNum = GPBFieldNumber(field);
  2936. result.impToAdd = imp_implementationWithBlock(^(id obj) {
  2937. return GPBGetHasIvar(obj, index, fieldNum);
  2938. });
  2939. result.encodingSelector = @selector(getBool);
  2940. break;
  2941. } else if (sel == field->setHasSel_) {
  2942. result.impToAdd = imp_implementationWithBlock(^(id obj, BOOL value) {
  2943. if (value) {
  2944. [NSException raise:NSInvalidArgumentException
  2945. format:@"%@: %@ can only be set to NO (to clear field).",
  2946. [obj class],
  2947. NSStringFromSelector(field->setHasSel_)];
  2948. }
  2949. GPBClearMessageField(obj, field);
  2950. });
  2951. result.encodingSelector = @selector(setBool:);
  2952. break;
  2953. } else {
  2954. GPBOneofDescriptor *oneof = field->containingOneof_;
  2955. if (oneof && (sel == oneof->caseSel_)) {
  2956. int32_t index = GPBFieldHasIndex(field);
  2957. result.impToAdd = imp_implementationWithBlock(^(id obj) {
  2958. return GPBGetHasOneof(obj, index);
  2959. });
  2960. result.encodingSelector = @selector(getEnum);
  2961. break;
  2962. }
  2963. }
  2964. } else {
  2965. // map<>/repeated fields.
  2966. if (sel == field->getSel_) {
  2967. if (field.fieldType == GPBFieldTypeRepeated) {
  2968. result.impToAdd = imp_implementationWithBlock(^(id obj) {
  2969. return GetArrayIvarWithField(obj, field);
  2970. });
  2971. } else {
  2972. result.impToAdd = imp_implementationWithBlock(^(id obj) {
  2973. return GetMapIvarWithField(obj, field);
  2974. });
  2975. }
  2976. result.encodingSelector = @selector(getArray);
  2977. break;
  2978. } else if (sel == field->setSel_) {
  2979. // Local for syntax so the block can directly capture it and not the
  2980. // full lookup.
  2981. result.impToAdd = imp_implementationWithBlock(^(id obj, id value) {
  2982. GPBSetObjectIvarWithFieldPrivate(obj, field, value);
  2983. });
  2984. result.encodingSelector = @selector(setArray:);
  2985. break;
  2986. } else if (sel == field->hasOrCountSel_) {
  2987. result.impToAdd = imp_implementationWithBlock(^(id obj) {
  2988. // Type doesn't matter, all *Array and *Dictionary types support
  2989. // -count.
  2990. NSArray *arrayOrMap =
  2991. GPBGetObjectIvarWithFieldNoAutocreate(obj, field);
  2992. return [arrayOrMap count];
  2993. });
  2994. result.encodingSelector = @selector(getArrayCount);
  2995. break;
  2996. }
  2997. }
  2998. }
  2999. if (result.impToAdd) {
  3000. const char *encoding =
  3001. GPBMessageEncodingForSelector(result.encodingSelector, YES);
  3002. Class msgClass = descriptor.messageClass;
  3003. BOOL methodAdded = class_addMethod(msgClass, sel, result.impToAdd, encoding);
  3004. // class_addMethod() is documented as also failing if the method was already
  3005. // added; so we check if the method is already there and return success so
  3006. // the method dispatch will still happen. Why would it already be added?
  3007. // Two threads could cause the same method to be bound at the same time,
  3008. // but only one will actually bind it; the other still needs to return true
  3009. // so things will dispatch.
  3010. if (!methodAdded) {
  3011. methodAdded = GPBClassHasSel(msgClass, sel);
  3012. }
  3013. return methodAdded;
  3014. }
  3015. return [super resolveInstanceMethod:sel];
  3016. }
  3017. + (BOOL)resolveClassMethod:(SEL)sel {
  3018. // Extensions scoped to a Message and looked up via class methods.
  3019. if (GPBResolveExtensionClassMethod(self, sel)) {
  3020. return YES;
  3021. }
  3022. return [super resolveClassMethod:sel];
  3023. }
  3024. #pragma mark - NSCoding Support
  3025. + (BOOL)supportsSecureCoding {
  3026. return YES;
  3027. }
  3028. - (instancetype)initWithCoder:(NSCoder *)aDecoder {
  3029. self = [self init];
  3030. if (self) {
  3031. NSData *data =
  3032. [aDecoder decodeObjectOfClass:[NSData class] forKey:kGPBDataCoderKey];
  3033. if (data.length) {
  3034. [self mergeFromData:data extensionRegistry:nil];
  3035. }
  3036. }
  3037. return self;
  3038. }
  3039. - (void)encodeWithCoder:(NSCoder *)aCoder {
  3040. #if defined(DEBUG) && DEBUG
  3041. if (extensionMap_.count) {
  3042. // Hint to go along with the docs on GPBMessage about this.
  3043. //
  3044. // Note: This is incomplete, in that it only checked the "root" message,
  3045. // if a sub message in a field has extensions, the issue still exists. A
  3046. // recursive check could be done here (like the work in
  3047. // GPBMessageDropUnknownFieldsRecursively()), but that has the potential to
  3048. // be expensive and could slow down serialization in DEBUG enought to cause
  3049. // developers other problems.
  3050. NSLog(@"Warning: writing out a GPBMessage (%@) via NSCoding and it"
  3051. @" has %ld extensions; when read back in, those fields will be"
  3052. @" in the unknownFields property instead.",
  3053. [self class], (long)extensionMap_.count);
  3054. }
  3055. #endif
  3056. NSData *data = [self data];
  3057. if (data.length) {
  3058. [aCoder encodeObject:data forKey:kGPBDataCoderKey];
  3059. }
  3060. }
  3061. #pragma mark - KVC Support
  3062. + (BOOL)accessInstanceVariablesDirectly {
  3063. // Make sure KVC doesn't use instance variables.
  3064. return NO;
  3065. }
  3066. @end
  3067. #pragma mark - Messages from GPBUtilities.h but defined here for access to helpers.
  3068. // Only exists for public api, no core code should use this.
  3069. id GPBGetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field) {
  3070. #if defined(DEBUG) && DEBUG
  3071. if (field.fieldType != GPBFieldTypeRepeated) {
  3072. [NSException raise:NSInvalidArgumentException
  3073. format:@"%@.%@ is not a repeated field.",
  3074. [self class], field.name];
  3075. }
  3076. #endif
  3077. return GetOrCreateArrayIvarWithField(self, field);
  3078. }
  3079. // Only exists for public api, no core code should use this.
  3080. id GPBGetMessageMapField(GPBMessage *self, GPBFieldDescriptor *field) {
  3081. #if defined(DEBUG) && DEBUG
  3082. if (field.fieldType != GPBFieldTypeMap) {
  3083. [NSException raise:NSInvalidArgumentException
  3084. format:@"%@.%@ is not a map<> field.",
  3085. [self class], field.name];
  3086. }
  3087. #endif
  3088. return GetOrCreateMapIvarWithField(self, field);
  3089. }
  3090. id GPBGetObjectIvarWithField(GPBMessage *self, GPBFieldDescriptor *field) {
  3091. NSCAssert(!GPBFieldIsMapOrArray(field), @"Shouldn't get here");
  3092. if (GPBGetHasIvarField(self, field)) {
  3093. uint8_t *storage = (uint8_t *)self->messageStorage_;
  3094. id *typePtr = (id *)&storage[field->description_->offset];
  3095. return *typePtr;
  3096. }
  3097. // Not set...
  3098. // Non messages (string/data), get their default.
  3099. if (!GPBFieldDataTypeIsMessage(field)) {
  3100. return field.defaultValue.valueMessage;
  3101. }
  3102. GPBPrepareReadOnlySemaphore(self);
  3103. dispatch_semaphore_wait(self->readOnlySemaphore_, DISPATCH_TIME_FOREVER);
  3104. GPBMessage *result = GPBGetObjectIvarWithFieldNoAutocreate(self, field);
  3105. if (!result) {
  3106. // For non repeated messages, create the object, set it and return it.
  3107. // This object will not initially be visible via GPBGetHasIvar, so
  3108. // we save its creator so it can become visible if it's mutated later.
  3109. result = GPBCreateMessageWithAutocreator(field.msgClass, self, field);
  3110. GPBSetAutocreatedRetainedObjectIvarWithField(self, field, result);
  3111. }
  3112. dispatch_semaphore_signal(self->readOnlySemaphore_);
  3113. return result;
  3114. }
  3115. #pragma clang diagnostic pop