Re: troublesome inputs - Mailing list pgsql-general
From | Lincoln Yeoh |
---|---|
Subject | Re: troublesome inputs |
Date | |
Msg-id | 3.0.5.32.20010218193222.00cf9210@192.228.128.13 Whole thread Raw |
In response to | troublesome inputs (Michelle Murrain <mpm@norwottuck.com>) |
List | pgsql-general |
At 02:49 PM 2/17/01 -0500, Michelle Murrain wrote: >in an unrecoverable error. What I need to do is two-fold - escape stuff that >is easy (like single quotes), and do testing of types (make sure they are not >putting non-numerics in int fields, etc.) > >I'm not a newbie at either perl or pgsql, but I'm definitely not yet a guru. > >I've identified quotes in particualr as characters I need to make sure >get taken care of in some way or another before I pass them to a query. Are >there others that folks know about, especially combinations of characters >that lead to wierdness? > >Other things I should be thinking about? What you should also think about are cases where people intentionally try to abuse your program. Generally you filter what goes into your program so that your program can handle it (input filtering). Then you filter what leaves your program for another program (output filtering). And you have to assume that your user can send you whatever they want. For example in a web app, if you store stuff in hidden form fields, the user can always save the form, alter the values and submit it to you. Same goes for storing stuff in cookies, or trying to limit options by limiting the options shown in HTML (users can always add more options, or even do multiple ones ;) ). **Input filtering For example in perl if you are using CGI what you can start with is: $CGI::POST_MAX=$MAXBUF; This limits the HTTP posts somewhat. HTTP GETs are usually limited by the webserver (if it's a decent one). Then you can do stuff like: sub myparam { $cgiparamname=shift; $defaultvalue=shift; $usermaxlength=shift||8; $userminlength=shift||0; $temp=param($cgiparamname); unless (defined(temp)) { $temp=$defaultvalue; } $value=substr($temp,0,$usermaxlength); $value=~tr/A-Za-z0-9//cd; if ($value ne $temp) return ($value,INFO_LOSS); if (length($value)<$userminlength) return ($value,TOO_SHORT); return $value,OK; } where value is assumed to be an alphanumeric. **Output filtering For perl you should use the built-in DBI quoting function, or use bind vars to stuff things into the database (after clamping down data to sane sizes/values first). Also, the DBI quoting feature doesn't quote %. So if you are going to use LIKE queries and you don't want to allow users to do full table scans you better limit how the % can appear, or just quote all occurences of % out. Personally I prefer to support a * for wildcard, and translate the * to % for the user with the usual sanity checks. This provides a useful layer of abstraction. When you are printing stuff out, make sure you quote it so that the web browser sees it correctly - e.g. not HTML if it's not supposed to be html. Similarly when you are printing a URL out. **Really troublesome stuff. I'm not sure how to quote or filter Unicode/custom encoded stuff properly. For example if a person sends some encoded stuff, and it's fine to your program, but when you pass it to another program, it decodes the info, and stuff may go boom (e.g. for instance document paths suddenly look like ../../../bankdirectory/bankkeys). I don't have any experience in dealing with this - it looks like a real pain. Basically I've been avoiding the problem by not supporting it (I only support known safe subsets of ASCII), but of course one day I'll have to. Any ideas on how to do it securely are very welcome. Cheerio, Link.
pgsql-general by date: