Right. I took "option" out for some reason. The following definitions have the desired behavior. I also added a base case to fromTo because otherwise the call to count would consume m tokens even if n-m < 0, which is probably not what we'd expect.

upTo :: Int -> GenParser tok st a -> GenParser tok st [a]
upTo n p
    | n <= 0 = return []
    | otherwise = option [] $ liftM2 (:) p (upTo (n-1) p)

fromTo :: Int -> Int -> GenParser tok st a -> GenParser tok st [a]
fromTo m n p
    | n-m < 0 = return []
    | otherwise = liftM2 (++) (count m p) (upTo (n-m) p)

Thanks!


On Mon, Oct 19, 2009 at 12:55 PM, Chaddaï Fouché <chaddai.fouche@gmail.com> wrote:
On Mon, Oct 19, 2009 at 6:22 PM, Ashish Agarwal <agarwal1975@gmail.com> wrote:
> The semantics of (upTo n p) should be to parse at most n tokens, but if less
> than n tokens are available that should still be a successful parse. And the
> next token should be the first one upTo failed on.
> I attempted to use the "try" parser in various locations but that doesn't
> seem to help, or maybe I'm using it incorrectly.


First, you should probably use pattern matching rather than if for
your base case/recursive case distinction, it's clearer (at least most
Haskellers seems to think it is) :

> upTo 0 p = return []

second, option was conceived for these case where you want to try a
parser and returns something if it fail :

> upTo n p = option [] $ liftM2 (:) p (upTo (n-1) p)

Even then, be careful of putting a try before any multi-token parser
that could fail harmlessly during the upTo.

--
Jedaï