arachni 1.2.1 → 1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (373) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +66 -0
  3. data/Gemfile +1 -1
  4. data/README.md +16 -5
  5. data/components/checks/active/ldap_injection/errors.txt +1 -0
  6. data/components/checks/active/source_code_disclosure.rb +1 -1
  7. data/components/checks/active/unvalidated_redirect.rb +6 -6
  8. data/components/checks/active/unvalidated_redirect_dom.rb +10 -7
  9. data/components/checks/passive/grep/captcha.rb +14 -5
  10. data/components/checks/passive/grep/form_upload.rb +7 -3
  11. data/components/checks/passive/grep/hsts.rb +3 -3
  12. data/components/checks/passive/grep/html_objects.rb +2 -3
  13. data/components/checks/passive/grep/http_only_cookies.rb +2 -3
  14. data/components/checks/passive/grep/insecure_cookies.rb +1 -1
  15. data/components/checks/passive/grep/password_autocomplete.rb +2 -2
  16. data/components/checks/passive/grep/unencrypted_password_forms.rb +7 -7
  17. data/components/checks/passive/grep/x_frame_options.rb +2 -2
  18. data/components/checks/passive/http_put.rb +2 -3
  19. data/components/path_extractors/comments.rb +3 -3
  20. data/components/path_extractors/scripts.rb +10 -1
  21. data/components/plugins/defaults/autothrottle.rb +27 -18
  22. data/components/plugins/defaults/meta/remedies/discovery.rb +30 -33
  23. data/components/plugins/defaults/meta/remedies/timing_attacks.rb +7 -11
  24. data/components/plugins/login_script.rb +9 -3
  25. data/components/plugins/proxy.rb +4 -3
  26. data/components/reporters/html.rb +11 -14
  27. data/components/reporters/html/default/issue.erb +13 -38
  28. data/components/reporters/html/default/issue/info.erb +1 -1
  29. data/components/reporters/html/default/summary/issues/by_name.erb +3 -3
  30. data/components/reporters/stdout.rb +62 -71
  31. data/components/reporters/xml.rb +26 -40
  32. data/components/reporters/xml/schema.xsd +43 -89
  33. data/lib/arachni/browser.rb +52 -3
  34. data/lib/arachni/browser/javascript.rb +3 -3
  35. data/lib/arachni/browser/javascript/scripts/taint_tracer.js +46 -25
  36. data/lib/arachni/browser_cluster.rb +61 -0
  37. data/lib/arachni/browser_cluster/job.rb +21 -1
  38. data/lib/arachni/browser_cluster/jobs/browser_provider.rb +3 -1
  39. data/lib/arachni/browser_cluster/jobs/resource_exploration.rb +2 -1
  40. data/lib/arachni/browser_cluster/jobs/resource_exploration/event_trigger.rb +2 -1
  41. data/lib/arachni/browser_cluster/jobs/taint_trace.rb +3 -2
  42. data/lib/arachni/browser_cluster/jobs/taint_trace/event_trigger.rb +1 -1
  43. data/lib/arachni/browser_cluster/worker.rb +5 -0
  44. data/lib/arachni/check/auditor.rb +22 -12
  45. data/lib/arachni/data/framework.rb +13 -1
  46. data/lib/arachni/data/issues.rb +9 -25
  47. data/lib/arachni/element/base.rb +9 -3
  48. data/lib/arachni/element/capabilities/analyzable.rb +2 -6
  49. data/lib/arachni/element/capabilities/analyzable/differential.rb +24 -7
  50. data/lib/arachni/element/capabilities/analyzable/{taint.rb → signature.rb} +23 -23
  51. data/lib/arachni/element/capabilities/auditable.rb +0 -6
  52. data/lib/arachni/element/capabilities/dom_only.rb +61 -0
  53. data/lib/arachni/element/capabilities/with_dom.rb +3 -1
  54. data/lib/arachni/element/cookie.rb +35 -5
  55. data/lib/arachni/element/cookie/dom.rb +13 -4
  56. data/lib/arachni/element/{capabilities/auditable/dom.rb → dom.rb} +20 -68
  57. data/lib/arachni/element/dom/capabilities/auditable.rb +29 -0
  58. data/lib/arachni/element/dom/capabilities/inputtable.rb +27 -0
  59. data/lib/arachni/element/dom/capabilities/mutable.rb +21 -0
  60. data/lib/arachni/element/dom/capabilities/submittable.rb +52 -0
  61. data/lib/arachni/element/form.rb +12 -1
  62. data/lib/arachni/element/form/capabilities/mutable.rb +2 -1
  63. data/lib/arachni/element/form/capabilities/with_dom.rb +0 -1
  64. data/lib/arachni/element/form/dom.rb +9 -3
  65. data/lib/arachni/element/header.rb +14 -33
  66. data/lib/arachni/element/header/capabilities/inputtable.rb +29 -0
  67. data/lib/arachni/element/header/capabilities/mutable.rb +51 -0
  68. data/lib/arachni/element/input/dom.rb +71 -0
  69. data/lib/arachni/element/json.rb +2 -0
  70. data/lib/arachni/element/link.rb +3 -0
  71. data/lib/arachni/element/link/capabilities/with_dom.rb +0 -1
  72. data/lib/arachni/element/link/dom.rb +16 -3
  73. data/lib/arachni/element/link/dom/capabilities/submittable.rb +29 -0
  74. data/lib/arachni/element/link_template.rb +3 -5
  75. data/lib/arachni/element/link_template/capabilities/inputtable.rb +5 -0
  76. data/lib/arachni/element/link_template/capabilities/with_dom.rb +0 -1
  77. data/lib/arachni/element/link_template/dom.rb +16 -3
  78. data/lib/arachni/element/link_template/dom/capabilities/submittable.rb +29 -0
  79. data/lib/arachni/element/server.rb +3 -5
  80. data/lib/arachni/element/ui_form.rb +106 -0
  81. data/lib/arachni/element/ui_form/dom.rb +107 -0
  82. data/lib/arachni/element/ui_input.rb +62 -0
  83. data/lib/arachni/element/xml.rb +2 -1
  84. data/lib/arachni/framework.rb +7 -5
  85. data/lib/arachni/framework/parts/audit.rb +0 -1
  86. data/lib/arachni/framework/parts/check.rb +1 -0
  87. data/lib/arachni/framework/parts/data.rb +4 -0
  88. data/lib/arachni/framework/parts/state.rb +0 -2
  89. data/lib/arachni/http/client.rb +17 -6
  90. data/lib/arachni/http/proxy_server.rb +52 -5
  91. data/lib/arachni/http/request.rb +1 -1
  92. data/lib/arachni/issue.rb +34 -179
  93. data/lib/arachni/issue/severity.rb +2 -0
  94. data/lib/arachni/option_groups/audit.rb +22 -2
  95. data/lib/arachni/option_groups/browser_cluster.rb +15 -0
  96. data/lib/arachni/page.rb +3 -2
  97. data/lib/arachni/parser.rb +24 -5
  98. data/lib/arachni/platform/manager.rb +1 -2
  99. data/lib/arachni/rpc/server/framework.rb +3 -4
  100. data/lib/arachni/rpc/server/framework/multi_instance.rb +2 -1
  101. data/lib/arachni/session.rb +1 -1
  102. data/lib/arachni/trainer.rb +4 -7
  103. data/lib/arachni/watir/element.rb +12 -1
  104. data/lib/version +1 -1
  105. data/spec/arachni/browser/element_locator_spec.rb +43 -43
  106. data/spec/arachni/browser/javascript/dom_monitor_spec.rb +44 -44
  107. data/spec/arachni/browser/javascript/proxy/stub_spec.rb +17 -14
  108. data/spec/arachni/browser/javascript/proxy_spec.rb +24 -24
  109. data/spec/arachni/browser/javascript/taint_tracer/frame/called_function_spec.rb +11 -11
  110. data/spec/arachni/browser/javascript/taint_tracer/frame_spec.rb +7 -7
  111. data/spec/arachni/browser/javascript/taint_tracer/sink/data_flow_spec.rb +13 -13
  112. data/spec/arachni/browser/javascript/taint_tracer/sink/execution_flow_spec.rb +7 -7
  113. data/spec/arachni/browser/javascript/taint_tracer_spec.rb +568 -558
  114. data/spec/arachni/browser/javascript_spec.rb +73 -63
  115. data/spec/arachni/browser_cluster/job/result_spec.rb +3 -3
  116. data/spec/arachni/browser_cluster/job_spec.rb +68 -48
  117. data/spec/arachni/browser_cluster/jobs/resource_exploration/event_trigger/result_spec.rb +2 -2
  118. data/spec/arachni/browser_cluster/jobs/resource_exploration/event_trigger_spec.rb +5 -4
  119. data/spec/arachni/browser_cluster/jobs/resource_exploration/result_spec.rb +2 -2
  120. data/spec/arachni/browser_cluster/jobs/resource_exploration_spec.rb +5 -5
  121. data/spec/arachni/browser_cluster/worker_spec.rb +87 -70
  122. data/spec/arachni/browser_cluster_spec.rb +64 -39
  123. data/spec/arachni/browser_spec.rb +692 -527
  124. data/spec/arachni/check/auditor_spec.rb +177 -147
  125. data/spec/arachni/check/base_spec.rb +33 -33
  126. data/spec/arachni/check/manager_spec.rb +15 -15
  127. data/spec/arachni/component/base_spec.rb +8 -8
  128. data/spec/arachni/component/manager_spec.rb +100 -99
  129. data/spec/arachni/component/options/address_spec.rb +3 -3
  130. data/spec/arachni/component/options/base_spec.rb +7 -7
  131. data/spec/arachni/component/options/bool_spec.rb +9 -9
  132. data/spec/arachni/component/options/float_spec.rb +6 -6
  133. data/spec/arachni/component/options/int_spec.rb +5 -5
  134. data/spec/arachni/component/options/multiple_choice_spec.rb +12 -12
  135. data/spec/arachni/component/options/object_spec.rb +2 -2
  136. data/spec/arachni/component/options/path_spec.rb +3 -3
  137. data/spec/arachni/component/options/port_spec.rb +5 -5
  138. data/spec/arachni/component/options/string_spec.rb +3 -3
  139. data/spec/arachni/component/options/url_spec.rb +4 -4
  140. data/spec/arachni/component/utilities_spec.rb +2 -2
  141. data/spec/arachni/data/framework/rpc_spec.rb +10 -9
  142. data/spec/arachni/data/framework_spec.rb +65 -46
  143. data/spec/arachni/data/issues_spec.rb +39 -77
  144. data/spec/arachni/data/plugins_spec.rb +11 -11
  145. data/spec/arachni/data/session_spec.rb +6 -6
  146. data/spec/arachni/data_spec.rb +8 -8
  147. data/spec/arachni/element/body_spec.rb +10 -10
  148. data/spec/arachni/element/capabilities/analyzable/differential_spec.rb +39 -21
  149. data/spec/arachni/element/capabilities/analyzable/{taint_spec.rb → signature_spec.rb} +63 -63
  150. data/spec/arachni/element/capabilities/analyzable/timeout_spec.rb +51 -51
  151. data/spec/arachni/element/capabilities/with_scope/scope_spec.rb +5 -5
  152. data/spec/arachni/element/cookie/dom_spec.rb +37 -18
  153. data/spec/arachni/element/cookie_spec.rb +206 -139
  154. data/spec/arachni/element/form/dom_spec.rb +36 -19
  155. data/spec/arachni/element/form_spec.rb +210 -187
  156. data/spec/arachni/element/generic_dom_spec.rb +14 -14
  157. data/spec/arachni/element/header_spec.rb +35 -17
  158. data/spec/arachni/element/json_spec.rb +53 -31
  159. data/spec/arachni/element/link/dom_spec.rb +46 -28
  160. data/spec/arachni/element/link_spec.rb +58 -40
  161. data/spec/arachni/element/link_template/dom_spec.rb +47 -29
  162. data/spec/arachni/element/link_template_spec.rb +79 -61
  163. data/spec/arachni/element/path_spec.rb +1 -1
  164. data/spec/arachni/element/server_spec.rb +33 -32
  165. data/spec/arachni/element/ui_form/ui_form_dom_spec.rb +164 -0
  166. data/spec/arachni/element/ui_form_spec.rb +242 -0
  167. data/spec/arachni/element/ui_input/dom_spec.rb +157 -0
  168. data/spec/arachni/element/ui_input_spec.rb +136 -0
  169. data/spec/arachni/element/xml_spec.rb +42 -24
  170. data/spec/arachni/element_filter_spec.rb +49 -48
  171. data/spec/arachni/error_spec.rb +3 -3
  172. data/spec/arachni/framework/parts/audit_spec.rb +64 -63
  173. data/spec/arachni/framework/parts/browser_spec.rb +16 -16
  174. data/spec/arachni/framework/parts/check_spec.rb +3 -3
  175. data/spec/arachni/framework/parts/data_spec.rb +48 -48
  176. data/spec/arachni/framework/parts/platform_spec.rb +3 -3
  177. data/spec/arachni/framework/parts/plugin_spec.rb +7 -6
  178. data/spec/arachni/framework/parts/report_spec.rb +7 -7
  179. data/spec/arachni/framework/parts/scope_spec.rb +16 -16
  180. data/spec/arachni/framework/parts/state_spec.rb +68 -69
  181. data/spec/arachni/framework_spec.rb +39 -31
  182. data/spec/arachni/http/client/dynamic_404_handlers_spec.rb +32 -32
  183. data/spec/arachni/http/client_spec.rb +219 -208
  184. data/spec/arachni/http/cookie_jar_spec.rb +72 -72
  185. data/spec/arachni/http/headers_spec.rb +14 -14
  186. data/spec/arachni/http/proxy_server_spec.rb +43 -42
  187. data/spec/arachni/http/request_spec.rb +105 -103
  188. data/spec/arachni/http/response/scope_spec.rb +24 -24
  189. data/spec/arachni/http/response_spec.rb +50 -49
  190. data/spec/arachni/issue/severity_spec.rb +10 -9
  191. data/spec/arachni/issue_spec.rb +71 -369
  192. data/spec/arachni/option_groups/audit_spec.rb +114 -114
  193. data/spec/arachni/option_groups/browser_cluster_spec.rb +20 -3
  194. data/spec/arachni/option_groups/datastore_spec.rb +6 -6
  195. data/spec/arachni/option_groups/dispatcher_spec.rb +19 -19
  196. data/spec/arachni/option_groups/http_spec.rb +11 -11
  197. data/spec/arachni/option_groups/input_spec.rb +31 -27
  198. data/spec/arachni/option_groups/output_spec.rb +2 -2
  199. data/spec/arachni/option_groups/paths_spec.rb +17 -17
  200. data/spec/arachni/option_groups/rpc_spec.rb +2 -2
  201. data/spec/arachni/option_groups/scope_spec.rb +40 -40
  202. data/spec/arachni/option_groups/session_spec.rb +6 -5
  203. data/spec/arachni/option_groups/snapshot_spec.rb +4 -4
  204. data/spec/arachni/options_spec.rb +46 -45
  205. data/spec/arachni/page/dom/transition_spec.rb +74 -72
  206. data/spec/arachni/page/dom_spec.rb +35 -35
  207. data/spec/arachni/page/scope_spec.rb +15 -15
  208. data/spec/arachni/page_spec.rb +217 -217
  209. data/spec/arachni/parser_spec.rb +106 -104
  210. data/spec/arachni/platform/fingerprinter_spec.rb +17 -14
  211. data/spec/arachni/platform/list_spec.rb +33 -33
  212. data/spec/arachni/platform/manager_spec.rb +67 -64
  213. data/spec/arachni/plugin/base_spec.rb +10 -10
  214. data/spec/arachni/plugin/manager_spec.rb +38 -37
  215. data/spec/arachni/report_spec.rb +43 -40
  216. data/spec/arachni/reporter/base_spec.rb +15 -15
  217. data/spec/arachni/reporter/manager_spec.rb +4 -4
  218. data/spec/arachni/reporter/options_spec.rb +6 -6
  219. data/spec/arachni/rpc/client/base_spec.rb +6 -6
  220. data/spec/arachni/rpc/client/dispatcher_spec.rb +2 -2
  221. data/spec/arachni/rpc/client/instance_spec.rb +6 -6
  222. data/spec/arachni/rpc/server/active_options_spec.rb +11 -8
  223. data/spec/arachni/rpc/server/base_spec.rb +5 -5
  224. data/spec/arachni/rpc/server/checks/manager_spec.rb +8 -8
  225. data/spec/arachni/rpc/server/dispatcher/node_spec.rb +37 -37
  226. data/spec/arachni/rpc/server/dispatcher/service_spec.rb +15 -14
  227. data/spec/arachni/rpc/server/dispatcher_spec.rb +36 -35
  228. data/spec/arachni/rpc/server/framework/distributor_spec.rb +36 -36
  229. data/spec/arachni/rpc/server/framework_multi_spec.rb +340 -336
  230. data/spec/arachni/rpc/server/framework_spec.rb +90 -85
  231. data/spec/arachni/rpc/server/instance_spec.rb +126 -107
  232. data/spec/arachni/rpc/server/output_spec.rb +1 -1
  233. data/spec/arachni/rpc/server/plugin/manager_spec.rb +6 -6
  234. data/spec/arachni/ruby/array_spec.rb +42 -42
  235. data/spec/arachni/ruby/hash_spec.rb +20 -18
  236. data/spec/arachni/ruby/io_spec.rb +2 -2
  237. data/spec/arachni/ruby/object_spec.rb +1 -1
  238. data/spec/arachni/ruby/set_spec.rb +3 -3
  239. data/spec/arachni/ruby/string_spec.rb +30 -30
  240. data/spec/arachni/ruby/webrick_spec.rb +2 -2
  241. data/spec/arachni/scope_spec.rb +1 -1
  242. data/spec/arachni/session_spec.rb +67 -64
  243. data/spec/arachni/snapshot_spec.rb +15 -15
  244. data/spec/arachni/state/audit_spec.rb +11 -11
  245. data/spec/arachni/state/element_filter_spec.rb +6 -6
  246. data/spec/arachni/state/framework/rpc_spec.rb +12 -12
  247. data/spec/arachni/state/framework_spec.rb +125 -121
  248. data/spec/arachni/state/http_spec.rb +7 -7
  249. data/spec/arachni/state/options_spec.rb +7 -7
  250. data/spec/arachni/state/plugins_spec.rb +8 -8
  251. data/spec/arachni/state_spec.rb +10 -10
  252. data/spec/arachni/support/buffer/autoflush_spec.rb +16 -16
  253. data/spec/arachni/support/buffer/base_spec.rb +39 -39
  254. data/spec/arachni/support/cache/least_cost_replacement_spec.rb +18 -18
  255. data/spec/arachni/support/cache/least_recently_pushed_spec.rb +24 -24
  256. data/spec/arachni/support/cache/least_recently_used_spec.rb +20 -20
  257. data/spec/arachni/support/cache/preference_spec.rb +4 -4
  258. data/spec/arachni/support/cache/random_replacement_spec.rb +8 -8
  259. data/spec/arachni/support/crypto/rsa_aes_cbc_spec.rb +1 -1
  260. data/spec/arachni/support/database/hash_spec.rb +44 -43
  261. data/spec/arachni/support/database/queue_spec.rb +27 -27
  262. data/spec/arachni/support/lookup/hash_set_spec.rb +8 -8
  263. data/spec/arachni/support/lookup/moolb_spec.rb +3 -3
  264. data/spec/arachni/support/mixins/observable_spec.rb +6 -6
  265. data/spec/arachni/support/signature_spec.rb +19 -19
  266. data/spec/arachni/trainer_spec.rb +39 -39
  267. data/spec/arachni/typhoeus/hydra_spec.rb +2 -2
  268. data/spec/arachni/uri/scope_spec.rb +66 -66
  269. data/spec/arachni/uri_spec.rb +107 -105
  270. data/spec/arachni/utilities_spec.rb +40 -40
  271. data/spec/components/checks/active/csrf_spec.rb +8 -8
  272. data/spec/components/checks/active/no_sql_injection_spec.rb +1 -1
  273. data/spec/components/checks/active/sql_injection_spec.rb +16 -16
  274. data/spec/components/checks/active/trainer_spec.rb +4 -4
  275. data/spec/components/checks/active/unvalidated_redirect_dom_spec.rb +4 -2
  276. data/spec/components/checks/active/xpath_injection_spec.rb +1 -1
  277. data/spec/components/checks/active/xss_dom_script_context_spec.rb +51 -21
  278. data/spec/components/checks/active/xss_dom_spec.rb +46 -24
  279. data/spec/components/checks/passive/allowed_methods_spec.rb +1 -1
  280. data/spec/components/checks/passive/grep/cookie_set_for_parent_domain_spec.rb +1 -1
  281. data/spec/components/checks/passive/grep/hsts_spec.rb +2 -2
  282. data/spec/components/checks/passive/grep/http_only_cookies_spec.rb +1 -1
  283. data/spec/components/checks/passive/grep/insecure_cookies_spec.rb +1 -1
  284. data/spec/components/checks/passive/grep/insecure_cors_policy_spec.rb +2 -2
  285. data/spec/components/checks/passive/grep/password_autocomplete_spec.rb +1 -1
  286. data/spec/components/checks/passive/grep/private_ip_spec.rb +3 -3
  287. data/spec/components/checks/passive/grep/unencrypted_password_forms_spec.rb +1 -1
  288. data/spec/components/checks/passive/grep/x_frame_options_spec.rb +2 -2
  289. data/spec/components/checks/passive/interesting_responses_spec.rb +2 -2
  290. data/spec/components/checks/passive/webdav_spec.rb +1 -1
  291. data/spec/components/checks/passive/xst_spec.rb +1 -1
  292. data/spec/components/fingerprinters/servers/apache_spec.rb +2 -2
  293. data/spec/components/path_extractors/comments_spec.rb +5 -1
  294. data/spec/components/path_extractors/scripts_spec.rb +5 -2
  295. data/spec/components/plugins/autologin_spec.rb +22 -22
  296. data/spec/components/plugins/autothrottle_spec.rb +6 -5
  297. data/spec/components/plugins/content_types_spec.rb +4 -4
  298. data/spec/components/plugins/cookie_collector_spec.rb +5 -5
  299. data/spec/components/plugins/exec_spec.rb +12 -12
  300. data/spec/components/plugins/form_dicattack_spec.rb +3 -3
  301. data/spec/components/plugins/headers_collector_spec.rb +8 -8
  302. data/spec/components/plugins/healthmap_spec.rb +3 -3
  303. data/spec/components/plugins/http_dicattack_spec.rb +3 -3
  304. data/spec/components/plugins/login_script_spec.rb +79 -22
  305. data/spec/components/plugins/meta/remedies/discovery_spec.rb +3 -2
  306. data/spec/components/plugins/meta/remedies/timing_attacks_spec.rb +3 -3
  307. data/spec/components/plugins/meta/uniformity_spec.rb +2 -2
  308. data/spec/components/plugins/restrict_to_dom_state_spec.rb +1 -1
  309. data/spec/components/plugins/script_spec.rb +1 -1
  310. data/spec/components/plugins/uncommon_headers_spec.rb +2 -2
  311. data/spec/components/plugins/vector_collector_spec.rb +2 -2
  312. data/spec/components/plugins/vector_feed_spec.rb +40 -40
  313. data/spec/components/plugins/waf_detector_spec.rb +6 -6
  314. data/spec/components/reporters/json_spec.rb +4 -4
  315. data/spec/components/reporters/marshal_spec.rb +2 -2
  316. data/spec/components/reporters/yaml_spec.rb +3 -2
  317. data/spec/external/wavsep/active/sqli_spec.rb +1 -3
  318. data/spec/spec_helper.rb +4 -0
  319. data/spec/support/factories/element/ui_form.rb +14 -0
  320. data/spec/support/factories/element/ui_input.rb +13 -0
  321. data/spec/support/factories/issue.rb +0 -13
  322. data/spec/support/fixtures/report.afr +0 -0
  323. data/spec/support/fixtures/{taint_check/taint.rb → signature_check/signature.rb} +2 -2
  324. data/spec/support/helpers/browser_cluster/jobs/taint_tracer.rb +11 -11
  325. data/spec/support/helpers/framework.rb +1 -1
  326. data/spec/support/helpers/pages.rb +2 -2
  327. data/spec/support/servers/arachni/browser.rb +139 -0
  328. data/spec/support/servers/arachni/browser/javascript/taint_tracer.rb +40 -0
  329. data/spec/support/servers/arachni/element/capabilities/analyzable/{taint.rb → signature.rb} +0 -0
  330. data/spec/support/servers/arachni/element/input/input_dom.rb +102 -0
  331. data/spec/support/servers/arachni/element/ui_form/ui_form_dom.rb +238 -0
  332. data/spec/support/servers/checks/active/trainer_check.rb +7 -7
  333. data/spec/support/servers/checks/active/unvalidated_redirect_dom.rb +22 -6
  334. data/spec/support/servers/checks/active/xss_dom.rb +50 -0
  335. data/spec/support/servers/checks/active/xss_dom_script_context.rb +53 -0
  336. data/spec/support/shared/browser/javascript/taint_tracer/sink/base.rb +6 -6
  337. data/spec/support/shared/check.rb +10 -12
  338. data/spec/support/shared/component/options/base.rb +24 -24
  339. data/spec/support/shared/element/base.rb +25 -25
  340. data/spec/support/shared/element/capabilities/auditable.rb +116 -140
  341. data/spec/support/shared/element/capabilities/dom_only.rb +65 -0
  342. data/spec/support/shared/element/capabilities/inputtable.rb +71 -86
  343. data/spec/support/shared/element/capabilities/mutable.rb +122 -111
  344. data/spec/support/shared/element/capabilities/refreshable.rb +10 -10
  345. data/spec/support/shared/element/capabilities/{submitable.rb → submittable.rb} +26 -26
  346. data/spec/support/shared/element/capabilities/with_auditor.rb +10 -10
  347. data/spec/support/shared/element/capabilities/with_dom.rb +8 -8
  348. data/spec/support/shared/element/capabilities/with_node.rb +4 -6
  349. data/spec/support/shared/element/capabilities/with_scope.rb +2 -2
  350. data/spec/support/shared/element/capabilities/with_source.rb +6 -8
  351. data/spec/support/shared/element/dom.rb +144 -0
  352. data/spec/support/shared/element/dom/auditable.rb +42 -0
  353. data/spec/support/shared/element/dom/inputtable.rb +5 -0
  354. data/spec/support/shared/element/dom/mutable.rb +3 -0
  355. data/spec/support/shared/element/dom/submittable.rb +119 -0
  356. data/spec/support/shared/external/wavsep.rb +3 -3
  357. data/spec/support/shared/fingerprinter.rb +2 -2
  358. data/spec/support/shared/framework.rb +1 -1
  359. data/spec/support/shared/http/message.rb +9 -9
  360. data/spec/support/shared/option_group.rb +17 -17
  361. data/spec/support/shared/path_extractor.rb +1 -1
  362. data/spec/support/shared/plugin.rb +2 -2
  363. data/spec/support/shared/support/cache.rb +57 -57
  364. data/spec/support/shared/support/lookup.rb +25 -25
  365. data/ui/cli/framework.rb +22 -11
  366. data/ui/cli/framework/option_parser.rb +15 -0
  367. data/ui/cli/option_parser.rb +8 -1
  368. data/ui/cli/output.rb +2 -1
  369. metadata +54 -20
  370. data/components/checks/active/xss_dom_inputs.rb +0 -236
  371. data/spec/components/checks/active/xss_dom_inputs_spec.rb +0 -30
  372. data/spec/support/servers/checks/active/xss_dom_inputs.rb +0 -59
  373. data/spec/support/shared/element/capabilities/auditable/dom.rb +0 -322
@@ -6,9 +6,6 @@
6
6
  web site for more information on licensing and terms of use.
7
7
  =end
8
8
 
9
- require_relative 'inputtable'
10
- require_relative 'mutable'
11
- require_relative 'submittable'
12
9
  require_relative 'with_auditor'
13
10
 
14
11
  module Arachni
@@ -20,9 +17,6 @@ module Element::Capabilities
20
17
  # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
21
18
  module Auditable
22
19
  include Utilities
23
- include Inputtable
24
- include Submittable
25
- include Mutable
26
20
  include WithAuditor
27
21
 
28
22
  # Load and include all available analysis/audit techniques.
@@ -0,0 +1,61 @@
1
+ =begin
2
+ Copyright 2010-2015 Tasos Laskos <tasos.laskos@arachni-scanner.com>
3
+
4
+ This file is part of the Arachni Framework project and is subject to
5
+ redistribution and commercial restrictions. Please see the Arachni Framework
6
+ web site for more information on licensing and terms of use.
7
+ =end
8
+
9
+ require_relative '../base'
10
+ require_relative 'with_node'
11
+ require_relative 'with_dom'
12
+
13
+ module Arachni
14
+ module Element::Capabilities
15
+
16
+ # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
17
+ module DOMOnly
18
+ include Arachni::Element::Capabilities::Inputtable
19
+ include Arachni::Element::Capabilities::WithNode
20
+ include Arachni::Element::Capabilities::WithDOM
21
+
22
+ attr_accessor :method
23
+
24
+ def initialize( options )
25
+ super options
26
+
27
+ @method = options[:method]
28
+
29
+ self.inputs = options[:inputs]
30
+ @default_inputs = self.inputs.dup.freeze
31
+ end
32
+
33
+ def mutation?
34
+ false
35
+ end
36
+
37
+ def coverage_id
38
+ dom.coverage_id
39
+ end
40
+
41
+ def coverage_hash
42
+ dom.coverage_hash
43
+ end
44
+
45
+ def id
46
+ dom.id
47
+ end
48
+
49
+ def dup
50
+ super.tap do |o|
51
+ o.method = self.method
52
+ end
53
+ end
54
+
55
+ def type
56
+ self.class.type
57
+ end
58
+
59
+ end
60
+ end
61
+ end
@@ -23,7 +23,9 @@ module WithDOM
23
23
  def dom
24
24
  return if skip_dom?
25
25
  @dom ||= self.class::DOM.new( parent: self )
26
- rescue Inputtable::Error
26
+ rescue Inputtable::Error => e
27
+ print_debug_exception e
28
+ nil
27
29
  end
28
30
 
29
31
  def skip_dom=( bool )
@@ -25,6 +25,8 @@ class Cookie < Base
25
25
  Dir.glob( lib ).each { |f| require f }
26
26
 
27
27
  # Generic element capabilities.
28
+ include Arachni::Element::Capabilities::Submittable
29
+ include Arachni::Element::Capabilities::Auditable
28
30
  include Arachni::Element::Capabilities::Analyzable
29
31
  include Arachni::Element::Capabilities::WithSource
30
32
 
@@ -33,6 +35,12 @@ class Cookie < Base
33
35
  include Capabilities::Inputtable
34
36
  include Capabilities::Mutable
35
37
 
38
+ ENCODE_CHARACTERS = ['+', ';', '%', "\0", '&', ' ', '"', "\n", "\r"]
39
+ ENCODE_CHARACTERS_LIST = ENCODE_CHARACTERS.join
40
+
41
+ ENCODE_CHARACTERS_IN_NAME = ENCODE_CHARACTERS + ['=']
42
+ ENCODE_CHARACTERS_IN_NAME_LIST = ENCODE_CHARACTERS_IN_NAME.join
43
+
36
44
  # Default cookie values
37
45
  DEFAULT = {
38
46
  name: nil,
@@ -163,7 +171,7 @@ class Cookie < Base
163
171
  # @return [String]
164
172
  # To be used in a `Cookie` HTTP request header.
165
173
  def to_s
166
- "#{encode( name )}=#{encode( value )}"
174
+ "#{encode( name, true )}=#{encode( value )}"
167
175
  end
168
176
 
169
177
  # @return [String]
@@ -404,13 +412,35 @@ class Cookie < Base
404
412
  #
405
413
  # @example
406
414
  # p Cookie.encode "+;%=\0 "
407
- # #=> "%2B%3B%25%3D%00%20"
415
+ # #=> "%2B%3B%25=%00+"
408
416
  #
417
+ # p Cookie.encode "+;%=\0 ", true
418
+ # #=> "%2B%3B%25%3D%00+"
409
419
  # @param [String] str
410
420
  #
411
421
  # @return [String]
412
- def encode( str )
413
- Arachni::HTTP::Request.encode( str )
422
+ def encode( str, name = false )
423
+ str = str.to_s
424
+
425
+ return str if !(name ? ENCODE_CHARACTERS_IN_NAME : ENCODE_CHARACTERS).
426
+ find { |c| str.include? c }
427
+
428
+ # Instead of just encoding everything we do this selectively because:
429
+ #
430
+ # * Some webapps don't actually decode some cookies, they just get
431
+ # the raw value, so if we encode something may break.
432
+ # * We need to encode spaces as '+' because of the above.
433
+ # Since we decode values, any un-encoded '+' will be converted
434
+ # to spaces, and in order to send back a value that the server
435
+ # expects we use '+' for spaces.
436
+
437
+ s = ::URI.encode(
438
+ str,
439
+ name ? ENCODE_CHARACTERS_IN_NAME_LIST :
440
+ ENCODE_CHARACTERS_LIST
441
+ )
442
+ s.gsub!( '%20', '+' )
443
+ s
414
444
  end
415
445
 
416
446
  # Decodes a {String} encoded for the `Cookie` header field.
@@ -423,7 +453,7 @@ class Cookie < Base
423
453
  #
424
454
  # @return [String]
425
455
  def decode( str )
426
- ::URI.decode_www_form_component str.to_s
456
+ Form.decode str
427
457
  end
428
458
 
429
459
  def keep_for_set_cookie
@@ -6,14 +6,19 @@
6
6
  web site for more information on licensing and terms of use.
7
7
  =end
8
8
 
9
+ require_relative '../dom'
10
+
9
11
  module Arachni::Element
10
12
  class Cookie
11
13
 
12
14
  # Provides access to DOM operations for {Cookie cookies}.
13
15
  #
14
16
  # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
15
- class DOM < Base
16
- include Arachni::Element::Capabilities::Auditable::DOM
17
+ class DOM < DOM
18
+ include Arachni::Element::DOM::Capabilities::Mutable
19
+ include Arachni::Element::DOM::Capabilities::Inputtable
20
+ include Arachni::Element::DOM::Capabilities::Submittable
21
+ include Arachni::Element::DOM::Capabilities::Auditable
17
22
 
18
23
  def initialize( options )
19
24
  super
@@ -24,8 +29,12 @@ class DOM < Base
24
29
 
25
30
  # Submits the cookie using the configured {#inputs}.
26
31
  def trigger
27
- browser.goto action, take_snapshot: false, cookies: self.inputs,
28
- update_transitions: false
32
+ [ browser.goto(
33
+ action,
34
+ take_snapshot: false,
35
+ cookies: self.inputs,
36
+ update_transitions: false
37
+ ) ]
29
38
  end
30
39
 
31
40
  def name
@@ -6,20 +6,18 @@
6
6
  web site for more information on licensing and terms of use.
7
7
  =end
8
8
 
9
- require 'forwardable'
9
+ require_relative 'base'
10
10
 
11
- module Arachni
12
- module Element::Capabilities
13
- module Auditable
11
+ module Arachni::Element
14
12
 
15
- # Provides access to DOM operations for {Element elements}.
16
- #
17
13
  # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
18
- module DOM
19
- include Auditable
20
- extend ::Forwardable
14
+ class DOM < Base
21
15
 
22
- INVALID_INPUT_DATA = [ "\0" ]
16
+ # load and include all available capabilities
17
+ lib = File.dirname( __FILE__ ) + '/dom/capabilities/*.rb'
18
+ Dir.glob( lib ).each { |f| require f }
19
+
20
+ include Arachni::Element::Capabilities::WithSource
23
21
 
24
22
  # @return [Element::Base]
25
23
  attr_accessor :parent
@@ -29,26 +27,6 @@ module DOM
29
27
 
30
28
  attr_reader :action
31
29
 
32
- # @!method with_browser_cluster( &block )
33
- def_delegator :auditor, :with_browser_cluster
34
-
35
- # @!method with_browser( &block )
36
- def_delegator :auditor, :with_browser
37
-
38
- def self.included( parent )
39
- parent.extend ClassMethods
40
- end
41
-
42
- module ClassMethods
43
- def encode( string )
44
- string
45
- end
46
-
47
- def decode( string )
48
- string
49
- end
50
- end
51
-
52
30
  def initialize( options )
53
31
  options = options.dup
54
32
  @parent = options.delete(:parent)
@@ -57,7 +35,7 @@ module DOM
57
35
  @url = parent.url.dup.freeze if parent.url
58
36
  @action = parent.action.dup.freeze if parent.action
59
37
  @page = parent.page if parent.page
60
- @source = parent.source.dup.freeze if parent.respond_to?(:source) && parent.source
38
+ @source = parent.source.dup.freeze if parent.respond_to?(:source) && parent.source
61
39
  else
62
40
  @url = options[:url].freeze
63
41
  @action = options[:action].freeze
@@ -76,10 +54,6 @@ module DOM
76
54
  # NOP
77
55
  end
78
56
 
79
- def valid_input_data?( data )
80
- !INVALID_INPUT_DATA.find { |c| data.include? c }
81
- end
82
-
83
57
  def page
84
58
  return @page if @page
85
59
  @page = parent.page if parent
@@ -90,29 +64,8 @@ module DOM
90
64
  @element ||= locate
91
65
  end
92
66
 
93
- # @param [Hash] options
94
- # @param [Block] block
95
- # Callback to be passed the evaluated {Page}.
96
- def submit( options = {}, &block )
97
- with_browser do |browser|
98
- prepare_browser( browser, options )
99
-
100
- # If we've wondered to an out-of-scope resource don't bother calling.
101
- # Can be caused by a JS redirect or something akin to that.
102
- if (transition = trigger)
103
- page = browser.to_page
104
- page.dom.transitions << transition
105
- block.call page.tap { |p| p.request.performer = self }
106
- end
107
-
108
- @element = nil
109
- @browser = nil
110
- end
111
- nil
112
- end
113
-
114
67
  def locator
115
- @locator ||= Browser::ElementLocator.from_node( node )
68
+ @locator ||= Arachni::Browser::ElementLocator.from_node( node )
116
69
  end
117
70
 
118
71
  # Locates the element in the page.
@@ -122,6 +75,8 @@ module DOM
122
75
 
123
76
  # Triggers the event on the subject {#element}.
124
77
  #
78
+ # @return [Array<Page::DOM::Transition>]
79
+ #
125
80
  # @abstract
126
81
  def trigger
127
82
  fail NotImplementedError
@@ -130,6 +85,7 @@ module DOM
130
85
  # Removes the associated {#page}, {#parent} and {#browser}
131
86
  def prepare_for_report
132
87
  super
88
+
133
89
  @page = nil
134
90
  @parent = nil
135
91
  @element = nil
@@ -146,9 +102,9 @@ module DOM
146
102
 
147
103
  def initialization_options
148
104
  options = {}
149
- options[:url] = url.dup if @url
105
+ options[:url] = @url.dup if @url
150
106
  options[:action] = @action.dup if @action
151
- options[:page] = page if page
107
+ # options[:page] = @page if @page
152
108
  options[:source] = @source.dup if @source
153
109
  options
154
110
  end
@@ -161,18 +117,14 @@ module DOM
161
117
  self.class.decode( string )
162
118
  end
163
119
 
164
- private
165
-
166
- def prepare_browser( browser, options )
167
- @browser = browser
168
- browser.javascript.custom_code = options[:custom_code]
169
- browser.javascript.taint = options[:taint]
120
+ def self.encode( string )
121
+ string
122
+ end
170
123
 
171
- browser.load page
124
+ def self.decode( string )
125
+ string
172
126
  end
173
127
 
174
128
  end
175
129
 
176
130
  end
177
- end
178
- end
@@ -0,0 +1,29 @@
1
+ =begin
2
+ Copyright 2010-2015 Tasos Laskos <tasos.laskos@arachni-scanner.com>
3
+
4
+ This file is part of the Arachni Framework project and is subject to
5
+ redistribution and commercial restrictions. Please see the Arachni Framework
6
+ web site for more information on licensing and terms of use.
7
+ =end
8
+
9
+ module Arachni::Element
10
+ class DOM
11
+ module Capabilities
12
+
13
+ # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
14
+ module Auditable
15
+ include Arachni::Element::Capabilities::Auditable
16
+
17
+ def with_browser( &block )
18
+ auditor.with_browser( &block )
19
+ end
20
+
21
+ def with_browser_cluster( &block )
22
+ auditor.with_browser_cluster( &block )
23
+ end
24
+
25
+ end
26
+
27
+ end
28
+ end
29
+ end
@@ -0,0 +1,27 @@
1
+ =begin
2
+ Copyright 2010-2015 Tasos Laskos <tasos.laskos@arachni-scanner.com>
3
+
4
+ This file is part of the Arachni Framework project and is subject to
5
+ redistribution and commercial restrictions. Please see the Arachni Framework
6
+ web site for more information on licensing and terms of use.
7
+ =end
8
+
9
+ module Arachni::Element
10
+ class DOM
11
+ module Capabilities
12
+
13
+ # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
14
+ module Inputtable
15
+ include Arachni::Element::Capabilities::Inputtable
16
+
17
+ INVALID_INPUT_DATA = [ "\0" ]
18
+
19
+ def valid_input_data?( data )
20
+ !INVALID_INPUT_DATA.find { |c| data.include? c }
21
+ end
22
+
23
+ end
24
+
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,21 @@
1
+ =begin
2
+ Copyright 2010-2015 Tasos Laskos <tasos.laskos@arachni-scanner.com>
3
+
4
+ This file is part of the Arachni Framework project and is subject to
5
+ redistribution and commercial restrictions. Please see the Arachni Framework
6
+ web site for more information on licensing and terms of use.
7
+ =end
8
+
9
+ module Arachni::Element
10
+ class DOM
11
+ module Capabilities
12
+
13
+ # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
14
+ module Mutable
15
+ include Arachni::Element::Capabilities::Mutable
16
+
17
+ end
18
+
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,52 @@
1
+ =begin
2
+ Copyright 2010-2015 Tasos Laskos <tasos.laskos@arachni-scanner.com>
3
+
4
+ This file is part of the Arachni Framework project and is subject to
5
+ redistribution and commercial restrictions. Please see the Arachni Framework
6
+ web site for more information on licensing and terms of use.
7
+ =end
8
+
9
+ module Arachni::Element
10
+ class DOM
11
+ module Capabilities
12
+
13
+ # @author Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>
14
+ module Submittable
15
+ include Arachni::Element::Capabilities::Submittable
16
+
17
+ # @param [Hash] options
18
+ # @param [Block] block
19
+ # Callback to be passed the evaluated {Page}.
20
+ def submit( options = {}, &block )
21
+ with_browser do |browser|
22
+ prepare_browser( browser, options )
23
+
24
+ # If we've wondered to an out-of-scope resource don't bother calling.
25
+ # Can be caused by a JS redirect or something akin to that.
26
+ if (transitions = self.trigger)
27
+ page = browser.to_page
28
+ page.dom.transitions += transitions
29
+ block.call page.tap { |p| p.request.performer = self }
30
+ end
31
+
32
+ @element = nil
33
+ @browser = nil
34
+ end
35
+ nil
36
+ end
37
+
38
+ private
39
+
40
+ def prepare_browser( browser, options )
41
+ @browser = browser
42
+ browser.javascript.custom_code = options[:custom_code]
43
+ browser.javascript.taint = options[:taint]
44
+
45
+ browser.load page
46
+ end
47
+
48
+ end
49
+
50
+ end
51
+ end
52
+ end