@@ -234,7 +234,7 @@ defmodule URI do
234234
235235 """
236236 def decode ( uri ) do
237- unpercent ( uri )
237+ unpercent ( uri , "" , false )
238238 catch
239239 :malformed_uri ->
240240 raise ArgumentError , "malformed URI #{ inspect uri } "
@@ -250,23 +250,25 @@ defmodule URI do
250250
251251 """
252252 def decode_www_form ( str ) do
253- String . split ( str , "+" ) |> Enum . map_join ( " " , & unpercent / 1 )
253+ unpercent ( str , "" , true )
254254 catch
255255 :malformed_uri ->
256256 raise ArgumentError , "malformed URI #{ inspect str } "
257257 end
258258
259- defp unpercent ( << ?% , hex_1 , hex_2 , tail :: binary >> ) do
260- << bsl ( hex_to_dec ( hex_1 ) , 4 ) + hex_to_dec ( hex_2 ) >> <> unpercent ( tail )
259+ defp unpercent ( << ?+ , tail :: binary >> , acc , spaces = true ) do
260+ unpercent ( tail , << acc :: binary , ?\s >> , spaces )
261261 end
262- defp unpercent ( << ?% , _ >> ) , do: throw ( :malformed_uri )
263- defp unpercent ( << ?% >> ) , do: throw ( :malformed_uri )
264262
265- defp unpercent ( << head , tail :: binary >> ) do
266- << head >> <> unpercent ( tail )
263+ defp unpercent ( << ?% , hex_1 , hex_2 , tail :: binary >> , acc , spaces ) do
264+ unpercent ( tail , << acc :: binary , bsl ( hex_to_dec ( hex_1 ) , 4 ) + hex_to_dec ( hex_2 ) >> , spaces )
267265 end
266+ defp unpercent ( << ?% , _ :: binary >> , _acc , _spaces ) , do: throw ( :malformed_uri )
268267
269- defp unpercent ( << >> ) , do: << >>
268+ defp unpercent ( << head , tail :: binary >> , acc , spaces ) do
269+ unpercent ( tail , << acc :: binary , head >> , spaces )
270+ end
271+ defp unpercent ( << >> , acc , _spaces ) , do: acc
270272
271273 defp hex_to_dec ( n ) when n in ?A .. ?F , do: n - ?A + 10
272274 defp hex_to_dec ( n ) when n in ?a .. ?f , do: n - ?a + 10
0 commit comments