howdy,

I was fiddling with this recently hoping to get an improved version into
view 1.3. there are different thoughts on 'decode-cgi should be a
higher/lower level function my belief is it should be pretty dumb and
just break strings up on a structural basis. but that leads to newby
biting which is not good. so here are two functions:

the first 'vet-word attempts to return as much of an input string! that
can be formed into a valid rebol word! making char replacements as needed.

the second is dumb but a robust decode-cgi that should handle all sorts
of malformed query strings,  which by default calls vet-word to filter
out funny stuff but can be called with a /raw refinement to skip it
if you feel you do not need the extra checks.

"mind the wrap"


vet-word: func[{return as much of a string is suitable to form a word
assumes no chars below 31 20x}
    str[string!]
    /local valid invalid result token
][
  invalid: make bitset! [#"@" #"#" #"$" #"%" #"^^" #"," #"[" #"]" #"("
#")" #"{" #"}" #"^"" #":" #";" #"/" #" " #"^/"]
  valid: complement invalid
  result: make string! length? str
  number: [copy token [opt["+" | "-"][integer! opt ["." integer!]]|["."
integer!]]
          (insert tail result join "number_" token)
  ]
  parse/all str[
      opt number
      any[ opt [[some invalid] (insert tail result "!")]
          copy token [some valid] (insert tail result token)
      ]
  ]
  if empty? result[result: "!"] ; if the string had no valid chars return
surprise

  if not equal? str result[print["IN-PUT " str newline "OUTPUT " result]];
debugging
  result
]

;;;----------------------------------------------------------------------------------------


decode-cgi: func [args [any-string!] /raw
    /local cgi-block name value mark here
][

all[empty? args return ""]
structural: make bitset! "+&=%"
non-struct: complement structural
xchar: make bitset! {0123456789ABCDEFabcdef}
safe-xchar: make bitset! {23456789ABCDEFabcdef}
cgi-block: make block! 16

spc: [mark: #"+" (change :mark " ")]
hex: [mark: #"%" 2 xchar (change/part :mark dehex copy/part :mark 3 3)
:mark]
safe-hex: [mark: #"%"
                 [safe-xchar xchar (change/part :mark dehex copy/part
:mark 3 3) :mark] |
                 [2 xchar (change :mark "!" )]
]
    parse/all args [
        opt "&"
        any[(name: copy "" value: copy "" here: copy "")
            copy name some  [non-struct | spc | safe-hex]
            (all[not raw name: vet-word trim name]
             either none?  here: find cgi-block to set-word! name[
               insert/only       tail cgi-block to set-word! name
               insert/only here: tail cgi-block none
            ][here: next here])
            opt[#"="
                opt[copy value some [non-struct | spc | hex]
                    (either none? first here
                        [change here value]
                        [either not block? first here
                            [poke here 1 to block! reduce[first here value]]
                            [insert/only tail first here value]
                        ]
                    )
                ]
            ]
            [ #"&" | end]
        ]
    ]
    cgi-block
]





On Mon, 9 Feb 2004, Hallvard Ystad wrote:

>
> Hi
>
> I know some people say "garbage in - garbage out", but one can't always control what 
> comes into one's programs as input. Here's what came to one of mine:
>
> http://www.bbc.co.uk/cgi-perl/h2/h2.cgi?state=threads&board=cult.tamaraswift&&sort=T
>
> This crashes 'decode-cgi in /core 2.5.6:
> >> decode-cgi "state=threads&board=cult.tamaraswift&&sort=T"
> ** Script Error: Out of range or past end
> ** Where: to-set-word
> ** Near: to set-word! :value
> >>
>
> I believe Andreas Bolka and/or Andrew Martin made a patch to 'decode-cgi some time 
> back, but can't seem to find it. Does anyone know whether the patch fixes this 
> problem? Or perhaps where I can find it?
>
> Thanks,
> HY
>
> Prętera censeo Carthaginem esse delendam
>
>
> --
> To unsubscribe from this list, just send an email to
> [EMAIL PROTECTED] with unsubscribe as the subject.
>
-- 
To unsubscribe from this list, just send an email to
[EMAIL PROTECTED] with unsubscribe as the subject.

Reply via email to