STUPID QUESTION TIME

and another long post - sorry.

Q - What stops Clojure's agent send-off function from becoming a DOS
("denial of service") vulnerability in a server?

This possibility occurred to me after reading several source files.

    * Stuart Sierra's HTTP client code in clojure-contrib
    * the Clojure source
        * src/clj/clojure/core.clj - the agent functions
        * src/jvm/clojure/lang/Agent.java

The send-off function:

    * calls Executors.newCachedThreadPool() factory function which
      returns an ExecutorService, one "that does not queue tasks but
      instead creates as many threads as are needed." [1]

    * is used instead of send "for actions that expect to block, as a
      file write might do." [2]

which makes it appropriate for the typical "network service" server.

        --------------------------------------------------

For that matter, since I am asking about agents, I may as well as my
next question instead of sending in a separate post.

Q - How exactly does an agent protect its "state" from concurrency
issues, particularly race conditions since I do not see any locking on
agents.

This question occurred to me as I was pondering how exactly I would
adapt the design for our current servers (C++) to Clojure.  I was led
to investigate what exactly agents do under the hood.

After some investigation, they seem to be a wrapper API over Java's
concurrency APIs.  Given that my investigation has led me to a
potentially overly simplistic interpretation of the agent
functionality, I am assuming a high probability that I am missing a
crucial bit of info.

Regardless, I was unable to find any code that seems to protect the
agent from simultaneous modification by multiple threads.  That's not
completely true.  In clojure.lang.Agent.dispatchAction(), I found that
code that checks for an in-flight transaction then adds the new Action
to transactions queue instead of what it would do otherwise (read the
code; I'll probably get it wrong anyway).

Finally, nowhere, in no example or source that I read, do I see a
transaction around the function that modifies the agent itself, which
leads me to surmise that the concurrency-protection must be
implemented in the agent's asynchrony (threading) code somewhere.  I
have not found it, though.

Which leads me to my final question:

Q - how exactly is an agent's state changed?  all of the agent docs
and APIs (that I have read (a lot)) describe their asynchrony, albeit
w/o much detail beyond the API itself.  Some of those including in
those descriptions changing the agent's state.  are they updated like
Refs?  like an ordinary Var?  they appear to be Refs.  they act like
Refs.  but NO docs nor examples show agents being protected.  So I am
a bit confused about this, too.

I'll make one last comment.  After reviewing the docs, examples and
the source, I realize that only the source has provided sufficient
detail to understand how agents work so that I can decide how they
might fit into the design for my servers.  For example, I would not
have known about the unlimited (?) thread-pool w/o reading the source.
Concurrency protection.  This being an open source project, I suppose
I can contribute by writing docs myself.  But if I am the only one
that is concerned w/ these details...

-robert

[1] Java in a Nutshell, 5th ed.; David Flanagan, 2005

[2] Programming Clojure; Stuart Hollaway, 2009

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to