appjam 0.1.8.8 → 0.1.8.9

Sign up to get free protection for your applications and to get access to all the features.
Files changed (168) hide show
  1. data/README.md +22 -62
  2. data/lib/appjam/generators/gist.yml +1 -1
  3. data/lib/appjam/generators/templates/blank/EiffelApplication.xcodeproj/project.pbxproj +1166 -482
  4. data/lib/appjam/generators/templates/blank/EiffelApplication.xcodeproj/project.xcworkspace/xcuserdata/eiffel.xcuserdatad/UserInterfaceState.xcuserstate +0 -0
  5. data/lib/appjam/generators/templates/blank/EiffelApplication/EiffelApplication-Prefix.pch.tt +26 -0
  6. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/AwesomeMenu.h +52 -0
  7. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/AwesomeMenu.m +412 -0
  8. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/AwesomeMenuItem.h +44 -0
  9. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/AwesomeMenuItem.m +97 -0
  10. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-addbutton-highlighted.png +0 -0
  11. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-addbutton-highlighted@2x.png +0 -0
  12. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-addbutton.png +0 -0
  13. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-addbutton@2x.png +0 -0
  14. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-menuitem-highlighted.png +0 -0
  15. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-menuitem-highlighted@2x.png +0 -0
  16. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-menuitem.png +0 -0
  17. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/bg-menuitem@2x.png +0 -0
  18. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/icon-plus-highlighted.png +0 -0
  19. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/icon-plus-highlighted@2x.png +0 -0
  20. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/icon-plus.png +0 -0
  21. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/icon-plus@2x.png +0 -0
  22. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/icon-star.png +0 -0
  23. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/AwesomeMenu/Images/icon-star@2x.png +0 -0
  24. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/CMPopTipView/CMPopTipView.h +167 -0
  25. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/CMPopTipView/CMPopTipView.m +639 -0
  26. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/FXLabel/FXLabel.h +97 -0
  27. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/FXLabel/FXLabel.m +1080 -0
  28. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/MBProgressHUD/MBProgressHUD.h +451 -0
  29. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/MBProgressHUD/MBProgressHUD.m +865 -0
  30. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/FacingView.h +42 -0
  31. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/FacingView.m +56 -0
  32. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/FoldView.h +90 -0
  33. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/FoldView.m +316 -0
  34. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/MultiFoldView.h +104 -0
  35. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/MultiFoldView.m +516 -0
  36. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldConstants.h +49 -0
  37. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldNavigationController.h +18 -0
  38. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldNavigationController.m +88 -0
  39. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldResources.bundle/swipe_guide_left.png +0 -0
  40. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldResources.bundle/swipe_guide_left@2x.png +0 -0
  41. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldResources.bundle/swipe_guide_right.png +0 -0
  42. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldResources.bundle/swipe_guide_right@2x.png +0 -0
  43. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldSwipeHintView.h +25 -0
  44. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldSwipeHintView.m +76 -0
  45. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldView.h +131 -0
  46. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/PaperFoldView.m +941 -0
  47. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/Resources/swipe_guide.psd +0 -0
  48. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/Resources/swipe_guide2.psd +0 -0
  49. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/ShadowView.h +46 -0
  50. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/ShadowView.m +82 -0
  51. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/TouchThroughUIView.h +39 -0
  52. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/TouchThroughUIView.m +72 -0
  53. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/UIView+Screenshot.h +42 -0
  54. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/PaperFold/UIView+Screenshot.m +100 -0
  55. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/NSBubbleData.h +34 -0
  56. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/NSBubbleData.m +140 -0
  57. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleHeaderTableViewCell.h +17 -0
  58. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleHeaderTableViewCell.m +57 -0
  59. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTableView.h +30 -0
  60. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTableView.m +233 -0
  61. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTableViewCell.h +19 -0
  62. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTableViewCell.m +122 -0
  63. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTableViewDataSource.h +24 -0
  64. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTypingTableViewCell.h +20 -0
  65. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/UIBubbleTypingTableViewCell.m +56 -0
  66. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/bubbleMine.png +0 -0
  67. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/bubbleMine@2x.png +0 -0
  68. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/bubbleSomeone.png +0 -0
  69. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/bubbleSomeone@2x.png +0 -0
  70. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/missingAvatar.png +0 -0
  71. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/missingAvatar@2x.png +0 -0
  72. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/typingMine.png +0 -0
  73. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/typingMine@2x.png +0 -0
  74. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/typingSomeone.png +0 -0
  75. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIBubbleTableView/images/typingSomeone@2x.png +0 -0
  76. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIGlossyButton/UIGlossyButton.h +124 -0
  77. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIGlossyButton/UIGlossyButton.m +545 -0
  78. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIGlossyButton/UIView+LayerEffects.h +22 -0
  79. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/components/UIGlossyButton/UIView+LayerEffects.m +32 -0
  80. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/AFIncrementalStore/AFIncrementalStore.h +344 -0
  81. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/AFIncrementalStore/AFIncrementalStore.m +848 -0
  82. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/AFIncrementalStore/AFRESTClient.h +135 -0
  83. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/AFIncrementalStore/AFRESTClient.m +441 -0
  84. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/InflectorKit/NSString+InflectorKit.h +40 -0
  85. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/InflectorKit/NSString+InflectorKit.m +36 -0
  86. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/InflectorKit/TTTStringInflector.h +76 -0
  87. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/InflectorKit/TTTStringInflector.m +270 -0
  88. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/MKAnnotationView+WebCache.h +95 -0
  89. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/MKAnnotationView+WebCache.m +78 -0
  90. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDImageCache.h +144 -0
  91. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDImageCache.m +311 -0
  92. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageCompat.h +40 -0
  93. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageCompat.m +54 -0
  94. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageDecoder.h +18 -0
  95. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageDecoder.m +70 -0
  96. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageDownloader.h +102 -0
  97. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageDownloader.m +226 -0
  98. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageDownloaderOperation.h +25 -0
  99. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageDownloaderOperation.m +339 -0
  100. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageManager.h +167 -0
  101. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageManager.m +244 -0
  102. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImageOperation.h +15 -0
  103. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImagePrefetcher.h +58 -0
  104. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/SDWebImagePrefetcher.m +127 -0
  105. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/UIButton+WebCache.h +173 -0
  106. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/UIButton+WebCache.m +129 -0
  107. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/UIImageView+WebCache.h +140 -0
  108. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/frameworks/SDWebImage/UIImageView+WebCache.m +84 -0
  109. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CPAnimationSequence/CPAnimationProgram.h +28 -0
  110. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CPAnimationSequence/CPAnimationSequence.h +28 -0
  111. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CPAnimationSequence/CPAnimationStep.h +49 -0
  112. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CPAnimationSequence/private/CPAnimationProgram.m +100 -0
  113. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CPAnimationSequence/private/CPAnimationSequence.m +85 -0
  114. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CPAnimationSequence/private/CPAnimationStep.m +122 -0
  115. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaAsyncSocket/GCDAsyncSocket.h +1074 -0
  116. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaAsyncSocket/GCDAsyncSocket.m +7430 -0
  117. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Categories/DDData.h +14 -0
  118. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Categories/DDData.m +158 -0
  119. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Categories/DDNumber.h +12 -0
  120. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Categories/DDNumber.m +88 -0
  121. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Categories/DDRange.h +56 -0
  122. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Categories/DDRange.m +104 -0
  123. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPAuthenticationRequest.h +45 -0
  124. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPAuthenticationRequest.m +195 -0
  125. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPConnection.h +119 -0
  126. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPConnection.m +2708 -0
  127. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPLogging.h +136 -0
  128. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPMessage.h +48 -0
  129. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPMessage.m +113 -0
  130. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPResponse.h +149 -0
  131. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPServer.h +205 -0
  132. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/HTTPServer.m +772 -0
  133. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Mime/MultipartFormDataParser.h +65 -0
  134. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Mime/MultipartFormDataParser.m +529 -0
  135. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Mime/MultipartMessageHeader.h +33 -0
  136. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Mime/MultipartMessageHeader.m +86 -0
  137. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Mime/MultipartMessageHeaderField.h +23 -0
  138. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Mime/MultipartMessageHeaderField.m +211 -0
  139. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPAsyncFileResponse.h +75 -0
  140. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPAsyncFileResponse.m +405 -0
  141. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPDataResponse.h +13 -0
  142. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPDataResponse.m +79 -0
  143. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPDynamicFileResponse.h +52 -0
  144. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPDynamicFileResponse.m +292 -0
  145. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPErrorResponse.h +9 -0
  146. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPErrorResponse.m +38 -0
  147. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPFileResponse.h +25 -0
  148. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPFileResponse.m +237 -0
  149. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPRedirectResponse.h +12 -0
  150. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/Responses/HTTPRedirectResponse.m +73 -0
  151. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/WebSocket.h +105 -0
  152. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Core/WebSocket.m +791 -0
  153. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/DAVConnection.h +7 -0
  154. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/DAVConnection.m +160 -0
  155. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/DAVResponse.h +11 -0
  156. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/DAVResponse.m +372 -0
  157. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/DELETEResponse.h +7 -0
  158. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/DELETEResponse.m +49 -0
  159. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/PUTResponse.h +8 -0
  160. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/CocoaHTTPServer/Extensions/WebDAV/PUTResponse.m +69 -0
  161. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/hpple/TFHpple.h +54 -0
  162. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/hpple/TFHpple.m +102 -0
  163. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/hpple/TFHppleElement.h +103 -0
  164. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/hpple/TFHppleElement.m +200 -0
  165. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/hpple/XPathQuery.h +10 -0
  166. data/lib/appjam/generators/templates/blank/EiffelApplication/libs/toolkit/hpple/XPathQuery.m +197 -0
  167. data/lib/appjam/version.rb +1 -1
  168. metadata +164 -3
@@ -0,0 +1,65 @@
1
+
2
+ #import "MultipartMessageHeader.h"
3
+
4
+ /*
5
+ Part one: http://tools.ietf.org/html/rfc2045 (Format of Internet Message Bodies)
6
+ Part two: http://tools.ietf.org/html/rfc2046 (Media Types)
7
+ Part three: http://tools.ietf.org/html/rfc2047 (Message Header Extensions for Non-ASCII Text)
8
+ Part four: http://tools.ietf.org/html/rfc4289 (Registration Procedures)
9
+ Part five: http://tools.ietf.org/html/rfc2049 (Conformance Criteria and Examples)
10
+
11
+ Internet message format: http://tools.ietf.org/html/rfc2822
12
+
13
+ Multipart/form-data http://tools.ietf.org/html/rfc2388
14
+ */
15
+
16
+ @class MultipartFormDataParser;
17
+
18
+ //-----------------------------------------------------------------
19
+ // protocol MultipartFormDataParser
20
+ //-----------------------------------------------------------------
21
+
22
+ @protocol MultipartFormDataParserDelegate <NSObject>
23
+ @optional
24
+ - (void) processContent:(NSData*) data WithHeader:(MultipartMessageHeader*) header;
25
+ - (void) processEndOfPartWithHeader:(MultipartMessageHeader*) header;
26
+ - (void) processPreambleData:(NSData*) data;
27
+ - (void) processEpilogueData:(NSData*) data;
28
+ - (void) processStartOfPartWithHeader:(MultipartMessageHeader*) header;
29
+ @end
30
+
31
+ //-----------------------------------------------------------------
32
+ // interface MultipartFormDataParser
33
+ //-----------------------------------------------------------------
34
+
35
+ @interface MultipartFormDataParser : NSObject {
36
+ NSMutableData* pendingData;
37
+ NSData* boundaryData;
38
+ MultipartMessageHeader* currentHeader;
39
+
40
+ BOOL waitingForCRLF;
41
+ BOOL reachedEpilogue;
42
+ BOOL processedPreamble;
43
+ BOOL checkForContentEnd;
44
+
45
+ #if __has_feature(objc_arc_weak)
46
+ __weak id<MultipartFormDataParserDelegate> delegate;
47
+ #else
48
+ __unsafe_unretained id<MultipartFormDataParserDelegate> delegate;
49
+ #endif
50
+ int currentEncoding;
51
+ NSStringEncoding formEncoding;
52
+ }
53
+
54
+ - (BOOL) appendData:(NSData*) data;
55
+
56
+ - (id) initWithBoundary:(NSString*) boundary formEncoding:(NSStringEncoding) formEncoding;
57
+
58
+ #if __has_feature(objc_arc_weak)
59
+ @property(weak, readwrite) id delegate;
60
+ #else
61
+ @property(unsafe_unretained, readwrite) id delegate;
62
+ #endif
63
+ @property(readwrite) NSStringEncoding formEncoding;
64
+
65
+ @end
@@ -0,0 +1,529 @@
1
+
2
+ #import "MultipartFormDataParser.h"
3
+ #import "DDData.h"
4
+ #import "HTTPLogging.h"
5
+
6
+ #pragma mark log level
7
+
8
+ #ifdef DEBUG
9
+ static const int httpLogLevel = HTTP_LOG_LEVEL_WARN;
10
+ #else
11
+ static const int httpLogLevel = HTTP_LOG_LEVEL_WARN;
12
+ #endif
13
+
14
+ #ifdef __x86_64__
15
+ #define FMTNSINT "li"
16
+ #else
17
+ #define FMTNSINT "i"
18
+ #endif
19
+
20
+
21
+ //-----------------------------------------------------------------
22
+ // interface MultipartFormDataParser (private)
23
+ //-----------------------------------------------------------------
24
+
25
+
26
+ @interface MultipartFormDataParser (private)
27
+ + (NSData*) decodedDataFromData:(NSData*) data encoding:(int) encoding;
28
+
29
+ - (int) findHeaderEnd:(NSData*) workingData fromOffset:(int) offset;
30
+ - (int) findContentEnd:(NSData*) data fromOffset:(int) offset;
31
+
32
+ - (int) numberOfBytesToLeavePendingWithData:(NSData*) data length:(NSUInteger) length encoding:(int) encoding;
33
+ - (int) offsetTillNewlineSinceOffset:(int) offset inData:(NSData*) data;
34
+
35
+ - (int) processPreamble:(NSData*) workingData;
36
+
37
+ @end
38
+
39
+
40
+ //-----------------------------------------------------------------
41
+ // implementation MultipartFormDataParser
42
+ //-----------------------------------------------------------------
43
+
44
+
45
+ @implementation MultipartFormDataParser
46
+ @synthesize delegate,formEncoding;
47
+
48
+ - (id) initWithBoundary:(NSString*) boundary formEncoding:(NSStringEncoding) _formEncoding {
49
+ if( nil == (self = [super init]) ){
50
+ return self;
51
+ }
52
+ if( nil == boundary ) {
53
+ HTTPLogWarn(@"MultipartFormDataParser: init with zero boundary");
54
+ return nil;
55
+ }
56
+ boundaryData = [[@"\r\n--" stringByAppendingString:boundary] dataUsingEncoding:NSASCIIStringEncoding];
57
+
58
+ pendingData = [[NSMutableData alloc] init];
59
+ currentEncoding = contentTransferEncoding_binary;
60
+ currentHeader = nil;
61
+
62
+ formEncoding = _formEncoding;
63
+ reachedEpilogue = NO;
64
+ processedPreamble = NO;
65
+
66
+ return self;
67
+ }
68
+
69
+
70
+ - (BOOL) appendData:(NSData *)data {
71
+ // Can't parse without boundary;
72
+ if( nil == boundaryData ) {
73
+ HTTPLogError(@"MultipartFormDataParser: Trying to parse multipart without specifying a valid boundary");
74
+ assert(false);
75
+ return NO;
76
+ }
77
+ NSData* workingData = data;
78
+
79
+ if( pendingData.length ) {
80
+ [pendingData appendData:data];
81
+ workingData = pendingData;
82
+ }
83
+
84
+ // the parser saves parse stat in the offset variable, which indicates offset of unhandled part in
85
+ // currently received chunk. Before returning, we always drop all data up to offset, leaving
86
+ // only unhandled for the next call
87
+
88
+ int offset = 0;
89
+
90
+ // don't parse data unless its size is greater then boundary length, so we couldn't
91
+ // misfind the boundary, if it got split into different data chunks
92
+ NSUInteger sizeToLeavePending = boundaryData.length;
93
+
94
+ if( !reachedEpilogue && workingData.length <= sizeToLeavePending ) {
95
+ // not enough data even to start parsing.
96
+ // save to pending data.
97
+ if( !pendingData.length ) {
98
+ [pendingData appendData:data];
99
+ }
100
+ if( checkForContentEnd ) {
101
+ if( pendingData.length >= 2 ) {
102
+ if( *(uint16_t*)(pendingData.bytes + offset) == 0x2D2D ) {
103
+ // we found the multipart end. all coming next is an epilogue.
104
+ HTTPLogVerbose(@"MultipartFormDataParser: End of multipart message");
105
+ waitingForCRLF = YES;
106
+ reachedEpilogue = YES;
107
+ offset+= 2;
108
+ }
109
+ else {
110
+ checkForContentEnd = NO;
111
+ waitingForCRLF = YES;
112
+ return YES;
113
+ }
114
+ } else {
115
+ return YES;
116
+ }
117
+
118
+ }
119
+ else {
120
+ return YES;
121
+ }
122
+ }
123
+ while( true ) {
124
+ if( checkForContentEnd ) {
125
+ // the flag will be raised to check if the last part was the last one.
126
+ if( offset < workingData.length -1 ) {
127
+ char* bytes = (char*) workingData.bytes;
128
+ if( *(uint16_t*)(bytes + offset) == 0x2D2D ) {
129
+ // we found the multipart end. all coming next is an epilogue.
130
+ HTTPLogVerbose(@"MultipartFormDataParser: End of multipart message");
131
+ checkForContentEnd = NO;
132
+ reachedEpilogue = YES;
133
+ // still wait for CRLF, that comes after boundary, but before epilogue.
134
+ waitingForCRLF = YES;
135
+ offset += 2;
136
+ }
137
+ else {
138
+ // it's not content end, we have to wait till separator line end before next part comes
139
+ waitingForCRLF = YES;
140
+ checkForContentEnd = NO;
141
+ }
142
+ }
143
+ else {
144
+ // we haven't got enough data to check for content end.
145
+ // save current unhandled data (it may be 1 byte) to pending and recheck on next chunk received
146
+ if( offset < workingData.length ) {
147
+ [pendingData setData:[NSData dataWithBytes:workingData.bytes + workingData.length-1 length:1]];
148
+ }
149
+ else {
150
+ // there is no unhandled data now, wait for more chunks
151
+ [pendingData setData:[NSData data]];
152
+ }
153
+ return YES;
154
+ }
155
+ }
156
+ if( waitingForCRLF ) {
157
+
158
+ // the flag will be raised in the code below, meaning, we've read the boundary, but
159
+ // didnt find the end of boundary line yet.
160
+
161
+ offset = [self offsetTillNewlineSinceOffset:offset inData:workingData];
162
+ if( -1 == offset ) {
163
+ // didnt find the endl again.
164
+ if( offset ) {
165
+ // we still have to save the unhandled data (maybe it's 1 byte CR)
166
+ if( *((char*)workingData.bytes + workingData.length -1) == '\r' ) {
167
+ [pendingData setData:[NSData dataWithBytes:workingData.bytes + workingData.length-1 length:1]];
168
+ }
169
+ else {
170
+ // or save nothing if it wasnt
171
+ [pendingData setData:[NSData data]];
172
+ }
173
+ }
174
+ return YES;
175
+ }
176
+ waitingForCRLF = NO;
177
+ }
178
+ if( !processedPreamble ) {
179
+ // got to find the first boundary before the actual content begins.
180
+ offset = [self processPreamble:workingData];
181
+ // wait for more data for preamble
182
+ if( -1 == offset )
183
+ return YES;
184
+ // invoke continue to skip newline after boundary.
185
+ continue;
186
+ }
187
+
188
+ if( reachedEpilogue ) {
189
+ // parse all epilogue data to delegate.
190
+ if( [delegate respondsToSelector:@selector(processEpilogueData:)] ) {
191
+ NSData* epilogueData = [NSData dataWithBytesNoCopy: (char*) workingData.bytes + offset length: workingData.length - offset freeWhenDone:NO];
192
+ [delegate processEpilogueData: epilogueData];
193
+ }
194
+ return YES;
195
+ }
196
+
197
+ if( nil == currentHeader ) {
198
+ // nil == currentHeader is a state flag, indicating we are waiting for header now.
199
+ // whenever part is over, currentHeader is set to nil.
200
+
201
+ // try to find CRLFCRLF bytes in the data, which indicates header end.
202
+ // we won't parse header parts, as they won't be too large.
203
+ int headerEnd = [self findHeaderEnd:workingData fromOffset:offset];
204
+ if( -1 == headerEnd ) {
205
+ // didn't recieve the full header yet.
206
+ if( !pendingData.length) {
207
+ // store the unprocessed data till next chunks come
208
+ [pendingData appendBytes:data.bytes + offset length:data.length - offset];
209
+ }
210
+ else {
211
+ if( offset ) {
212
+ // save the current parse state; drop all handled data and save unhandled only.
213
+ pendingData = [[NSMutableData alloc] initWithBytes: (char*) workingData.bytes + offset length:workingData.length - offset];
214
+ }
215
+ }
216
+ return YES;
217
+ }
218
+ else {
219
+
220
+ // let the header parser do it's job from now on.
221
+ NSData * headerData = [NSData dataWithBytesNoCopy: (char*) workingData.bytes + offset length:headerEnd + 2 - offset freeWhenDone:NO];
222
+ currentHeader = [[MultipartMessageHeader alloc] initWithData:headerData formEncoding:formEncoding];
223
+
224
+ if( nil == currentHeader ) {
225
+ // we've found the data is in wrong format.
226
+ HTTPLogError(@"MultipartFormDataParser: MultipartFormDataParser: wrong input format, coulnd't get a valid header");
227
+ return NO;
228
+ }
229
+ if( [delegate respondsToSelector:@selector(processStartOfPartWithHeader:)] ) {
230
+ [delegate processStartOfPartWithHeader:currentHeader];
231
+ }
232
+
233
+ HTTPLogVerbose(@"MultipartFormDataParser: MultipartFormDataParser: Retrieved part header.");
234
+ }
235
+ // skip the two trailing \r\n, in addition to the whole header.
236
+ offset = headerEnd + 4;
237
+ }
238
+ // after we've got the header, we try to
239
+ // find the boundary in the data.
240
+ int contentEnd = [self findContentEnd:workingData fromOffset:offset];
241
+
242
+ if( contentEnd == -1 ) {
243
+
244
+ // this case, we didn't find the boundary, so the data is related to the current part.
245
+ // we leave the sizeToLeavePending amount of bytes to make sure we don't include
246
+ // boundary part in processed data.
247
+ NSUInteger sizeToPass = workingData.length - offset - sizeToLeavePending;
248
+
249
+ // if we parse BASE64 encoded data, or Quoted-Printable data, we will make sure we don't break the format
250
+ int leaveTrailing = [self numberOfBytesToLeavePendingWithData:data length:sizeToPass encoding:currentEncoding];
251
+ sizeToPass -= leaveTrailing;
252
+
253
+ if( sizeToPass <= 0 ) {
254
+ // wait for more data!
255
+ if( offset ) {
256
+ [pendingData setData:[NSData dataWithBytes:(char*) workingData.bytes + offset length:workingData.length - offset]];
257
+ }
258
+ return YES;
259
+ }
260
+ // decode the chunk and let the delegate use it (store in a file, for example)
261
+ NSData* decodedData = [MultipartFormDataParser decodedDataFromData:[NSData dataWithBytesNoCopy:(char*)workingData.bytes + offset length:workingData.length - offset - sizeToLeavePending freeWhenDone:NO] encoding:currentEncoding];
262
+
263
+ if( [delegate respondsToSelector:@selector(processContent:WithHeader:)] ) {
264
+ HTTPLogVerbose(@"MultipartFormDataParser: Processed %"FMTNSINT" bytes of body",sizeToPass);
265
+
266
+ [delegate processContent: decodedData WithHeader:currentHeader];
267
+ }
268
+
269
+ // store the unprocessed data till the next chunks come.
270
+ [pendingData setData:[NSData dataWithBytes:(char*)workingData.bytes + workingData.length - sizeToLeavePending length:sizeToLeavePending]];
271
+ return YES;
272
+ }
273
+ else {
274
+
275
+ // Here we found the boundary.
276
+ // let the delegate process it, and continue going to the next parts.
277
+ if( [delegate respondsToSelector:@selector(processContent:WithHeader:)] ) {
278
+ [delegate processContent:[NSData dataWithBytesNoCopy:(char*) workingData.bytes + offset length:contentEnd - offset freeWhenDone:NO] WithHeader:currentHeader];
279
+ }
280
+
281
+ if( [delegate respondsToSelector:@selector(processEndOfPartWithHeader:)] ){
282
+ [delegate processEndOfPartWithHeader:currentHeader];
283
+ HTTPLogVerbose(@"MultipartFormDataParser: End of body part");
284
+ }
285
+ currentHeader = nil;
286
+
287
+ // set up offset to continue with the remaining data (if any)
288
+ // cast to int because above comment suggests a small number
289
+ offset = contentEnd + (int)boundaryData.length;
290
+ checkForContentEnd = YES;
291
+ // setting the flag tells the parser to skip all the data till CRLF
292
+ }
293
+ }
294
+ return YES;
295
+ }
296
+
297
+
298
+ //-----------------------------------------------------------------
299
+ #pragma mark private methods
300
+
301
+ - (int) offsetTillNewlineSinceOffset:(int) offset inData:(NSData*) data {
302
+ char* bytes = (char*) data.bytes;
303
+ NSUInteger length = data.length;
304
+ if( offset >= length - 1 )
305
+ return -1;
306
+
307
+ while ( *(uint16_t*)(bytes + offset) != 0x0A0D ) {
308
+ // find the trailing \r\n after the boundary. The boundary line might have any number of whitespaces before CRLF, according to rfc2046
309
+
310
+ // in debug, we might also want to know, if the file is somehow misformatted.
311
+ #ifdef DEBUG
312
+ if( !isspace(*(bytes+offset)) ) {
313
+ HTTPLogWarn(@"MultipartFormDataParser: Warning, non-whitespace character '%c' between boundary bytes and CRLF in boundary line",*(bytes+offset) );
314
+ }
315
+ if( !isspace(*(bytes+offset+1)) ) {
316
+ HTTPLogWarn(@"MultipartFormDataParser: Warning, non-whitespace character '%c' between boundary bytes and CRLF in boundary line",*(bytes+offset+1) );
317
+ }
318
+ #endif
319
+ offset++;
320
+ if( offset >= length ) {
321
+ // no endl found within current data
322
+ return -1;
323
+ }
324
+ }
325
+
326
+ offset += 2;
327
+ return offset;
328
+ }
329
+
330
+
331
+ - (int) processPreamble:(NSData*) data {
332
+ int offset = 0;
333
+
334
+ char* boundaryBytes = (char*) boundaryData.bytes + 2; // the first boundary won't have CRLF preceding.
335
+ char* dataBytes = (char*) data.bytes;
336
+ NSUInteger boundaryLength = boundaryData.length - 2;
337
+ NSUInteger dataLength = data.length;
338
+
339
+ // find the boundary without leading CRLF.
340
+ while( offset < dataLength - boundaryLength +1 ) {
341
+ int i;
342
+ for( i = 0;i < boundaryLength; i++ ) {
343
+ if( boundaryBytes[i] != dataBytes[offset + i] )
344
+ break;
345
+ }
346
+ if( i == boundaryLength ) {
347
+ break;
348
+ }
349
+ offset++;
350
+ }
351
+
352
+ if( offset == dataLength ) {
353
+ // the end of preamble wasn't found in this chunk
354
+ NSUInteger sizeToProcess = dataLength - boundaryLength;
355
+ if( sizeToProcess > 0) {
356
+ if( [delegate respondsToSelector:@selector(processPreambleData:)] ) {
357
+ NSData* preambleData = [NSData dataWithBytesNoCopy: (char*) data.bytes length: data.length - offset - boundaryLength freeWhenDone:NO];
358
+ [delegate processPreambleData:preambleData];
359
+ HTTPLogVerbose(@"MultipartFormDataParser: processed preamble");
360
+ }
361
+ pendingData = [NSMutableData dataWithBytes: data.bytes + data.length - boundaryLength length:boundaryLength];
362
+ }
363
+ return -1;
364
+ }
365
+ else {
366
+ if ( offset && [delegate respondsToSelector:@selector(processPreambleData:)] ) {
367
+ NSData* preambleData = [NSData dataWithBytesNoCopy: (char*) data.bytes length: offset freeWhenDone:NO];
368
+ [delegate processPreambleData:preambleData];
369
+ }
370
+ offset +=boundaryLength;
371
+ // tells to skip CRLF after the boundary.
372
+ processedPreamble = YES;
373
+ waitingForCRLF = YES;
374
+ }
375
+ return offset;
376
+ }
377
+
378
+
379
+
380
+ - (int) findHeaderEnd:(NSData*) workingData fromOffset:(int)offset {
381
+ char* bytes = (char*) workingData.bytes;
382
+ NSUInteger inputLength = workingData.length;
383
+ uint16_t separatorBytes = 0x0A0D;
384
+
385
+ while( true ) {
386
+ if(inputLength < offset + 3 ) {
387
+ // wait for more data
388
+ return -1;
389
+ }
390
+ if( (*((uint16_t*) (bytes+offset)) == separatorBytes) && (*((uint16_t*) (bytes+offset)+1) == separatorBytes) ) {
391
+ return offset;
392
+ }
393
+ offset++;
394
+ }
395
+ return -1;
396
+ }
397
+
398
+
399
+ - (int) findContentEnd:(NSData*) data fromOffset:(int) offset {
400
+ char* boundaryBytes = (char*) boundaryData.bytes;
401
+ char* dataBytes = (char*) data.bytes;
402
+ NSUInteger boundaryLength = boundaryData.length;
403
+ NSUInteger dataLength = data.length;
404
+
405
+ while( offset < dataLength - boundaryLength +1 ) {
406
+ int i;
407
+ for( i = 0;i < boundaryLength; i++ ) {
408
+ if( boundaryBytes[i] != dataBytes[offset + i] )
409
+ break;
410
+ }
411
+ if( i == boundaryLength ) {
412
+ return offset;
413
+ }
414
+ offset++;
415
+ }
416
+ return -1;
417
+ }
418
+
419
+
420
+ - (int) numberOfBytesToLeavePendingWithData:(NSData*) data length:(int) length encoding:(int) encoding {
421
+ // If we have BASE64 or Quoted-Printable encoded data, we have to be sure
422
+ // we don't break the format.
423
+ int sizeToLeavePending = 0;
424
+
425
+ if( encoding == contentTransferEncoding_base64 ) {
426
+ char* bytes = (char*) data.bytes;
427
+ int i;
428
+ for( i = length - 1; i > 0; i++ ) {
429
+ if( * (uint16_t*) (bytes + i) == 0x0A0D ) {
430
+ break;
431
+ }
432
+ }
433
+ // now we've got to be sure that the length of passed data since last line
434
+ // is multiplier of 4.
435
+ sizeToLeavePending = (length - i) & ~0x11; // size to leave pending = length-i - (length-i) %4;
436
+ return sizeToLeavePending;
437
+ }
438
+
439
+ if( encoding == contentTransferEncoding_quotedPrintable ) {
440
+ // we don't pass more less then 3 bytes anyway.
441
+ if( length <= 2 )
442
+ return length;
443
+ // check the last bytes to be start of encoded symbol.
444
+ const char* bytes = data.bytes + length - 2;
445
+ if( bytes[0] == '=' )
446
+ return 2;
447
+ if( bytes[1] == '=' )
448
+ return 1;
449
+ return 0;
450
+ }
451
+ return 0;
452
+ }
453
+
454
+
455
+ //-----------------------------------------------------------------
456
+ #pragma mark decoding
457
+
458
+
459
+ + (NSData*) decodedDataFromData:(NSData*) data encoding:(int) encoding {
460
+ switch (encoding) {
461
+ case contentTransferEncoding_base64: {
462
+ return [data base64Decoded];
463
+ } break;
464
+
465
+ case contentTransferEncoding_quotedPrintable: {
466
+ return [self decodedDataFromQuotedPrintableData:data];
467
+ } break;
468
+
469
+ default: {
470
+ return data;
471
+ } break;
472
+ }
473
+ }
474
+
475
+
476
+ + (NSData*) decodedDataFromQuotedPrintableData:(NSData *)data {
477
+ // http://tools.ietf.org/html/rfc2045#section-6.7
478
+
479
+ const char hex [] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F', };
480
+
481
+ NSMutableData* result = [[NSMutableData alloc] initWithLength:data.length];
482
+ const char* bytes = (const char*) data.bytes;
483
+ int count = 0;
484
+ NSUInteger length = data.length;
485
+ while( count < length ) {
486
+ if( bytes[count] == '=' ) {
487
+ [result appendBytes:bytes length:count];
488
+ bytes = bytes + count + 1;
489
+ length -= count + 1;
490
+ count = 0;
491
+
492
+ if( length < 3 ) {
493
+ HTTPLogWarn(@"MultipartFormDataParser: warning, trailing '=' in quoted printable data");
494
+ }
495
+ // soft newline
496
+ if( bytes[0] == '\r' ) {
497
+ bytes += 1;
498
+ if(bytes[1] == '\n' ) {
499
+ bytes += 2;
500
+ }
501
+ continue;
502
+ }
503
+ char encodedByte = 0;
504
+
505
+ for( int i = 0; i < sizeof(hex); i++ ) {
506
+ if( hex[i] == bytes[0] ) {
507
+ encodedByte += i << 4;
508
+ }
509
+ if( hex[i] == bytes[1] ) {
510
+ encodedByte += i;
511
+ }
512
+ }
513
+ [result appendBytes:&encodedByte length:1];
514
+ bytes += 2;
515
+ }
516
+
517
+ #ifdef DEBUG
518
+ if( (unsigned char) bytes[count] > 126 ) {
519
+ HTTPLogWarn(@"MultipartFormDataParser: Warning, character with code above 126 appears in quoted printable encoded data");
520
+ }
521
+ #endif
522
+
523
+ count++;
524
+ }
525
+ return result;
526
+ }
527
+
528
+
529
+ @end