1. A method for identifying and executing synchronized read regions and synchronized write regions in programming languages that offer synchronization but which do not offer programmers means to explicitly distinguish between such regions, said method comprising the steps of: (i) processing code of the program with a software tool to convert the code to an internal representation for the software tool; (ii) constructing a control flow graph of code blocks which also identifies entry and exit points for each region of code subject to a lock; (iii) for each code block in the control flow graph, performing visibility analysis to identify any of the code blocks whose execution by a thread will be visible to other threads and any of the code blocks whose execution may examine fields of the synchronized objects; (iv) moving each determined entry and exit point to enclose a smallest set of code blocks subject to a lock which can be achieved without altering semantics of the code of the program; (v) creating a set of trees comprising a unique tree representing a unique nested set of synchronized regions; (vi) for each tree created in (v), if the tree contains at least one block identified in step (iii) then marking the tree a write tree and otherwise marking the tree a read tree; and (vii) creating a write lock for the regions in each tree identified as a write tree and creating a read lock for the regions in each tree identified as a read tree.