Assuming the code in the question, use identical we can get its index like this:
Position(function(fun) identical(fun, foo), l)
## [1] 1
or
which(sapply(l, identical, foo))
## [1] 1
If you know something about the functions you may be able to run them and select based on the output.  For the example this works:
Position(function(f) length(f()), l)
## [1] 1
If you have control over the creation of the list an easy approach is to create the list with names:
l2 <- list(foo = foo, bar = bar)
nms <- setdiff(names(l2), "foo")
Removal
If we know that foo is in l once then
l[-ix]
or in the case of l2:
l2[nms]
or use the alternative given by @Gregor:
Filter(function(x) !identical(x, foo), l)
Edge cases
If foo might not be in l you will need to check that condition first. Position and match return NA if there is no match (or specify the nomatch argument to either) and which returns intetger(0) for a no match.  
If foo can be in l more than once then use the which alternative above.
Other
Note that which and Filter check every position but match and Position stop after the first match.