Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Merge branch 'S4U'
authorMartin Quinson <martin.quinson@loria.fr>
Tue, 13 Oct 2015 22:06:18 +0000 (00:06 +0200)
committerMartin Quinson <martin.quinson@loria.fr>
Tue, 13 Oct 2015 22:06:18 +0000 (00:06 +0200)
581 files changed:
.gitattributes [new file with mode: 0644]
.travis.yml
CMakeLists.txt
ChangeLog
NEWS
TODO
appveyor.yml
contrib/deployment_generation/generate_random_deployment.pl
contrib/network_model/regression2.py
contrib/psg/tutorial.odt
contrib/psg/tutorial.pdf
doc/Doxyfile.in
doc/Layout.xml
doc/doxygen/advanced.doc
doc/doxygen/deployment.doc
doc/doxygen/examples.doc [moved from doc/doxygen/use.doc with 73% similarity]
doc/doxygen/getting_started.doc
doc/doxygen/getting_started_index.doc [new file with mode: 0644]
doc/doxygen/help.doc
doc/doxygen/index.doc
doc/doxygen/inside_cmake.doc
doc/doxygen/inside_doxygen.doc
doc/doxygen/inside_extending.doc
doc/doxygen/internals.doc
doc/doxygen/introduction.doc
doc/doxygen/module-smpi.doc
doc/doxygen/module-xbt.doc
doc/doxygen/options.doc
doc/doxygen/platform.doc
doc/doxygen/pls.doc
doc/doxygen/stylesheet.css
doc/doxygen/tracing.doc
doc/msg-tuto-src/masterworker0.c
doc/msg-tuto-src/masterworker1.c
doc/msg-tuto-src/masterworker2.c
doc/msg-tuto-src/masterworker3.c
doc/msg-tuto-src/masterworker4.c
doc/webcruft/storage_sample_scenario.png [new file with mode: 0644]
examples/java/CMakeLists.txt
examples/java/async/CMakeLists.txt
examples/java/bittorrent/CMakeLists.txt
examples/java/bittorrent/generate.py
examples/java/chord/CMakeLists.txt
examples/java/cloud/CMakeLists.txt
examples/java/cloud/migration/CMakeLists.txt
examples/java/commTime/CMakeLists.txt
examples/java/io/CMakeLists.txt
examples/java/kademlia/CMakeLists.txt
examples/java/master_slave_bypass/CMakeLists.txt
examples/java/master_slave_kill/CMakeLists.txt
examples/java/masterslave/CMakeLists.txt
examples/java/migration/CMakeLists.txt
examples/java/mutualExclusion/CMakeLists.txt
examples/java/pingPong/CMakeLists.txt
examples/java/priority/CMakeLists.txt
examples/java/reservationSurfPlugin/CMakeLists.txt
examples/java/startKillTime/CMakeLists.txt
examples/java/surfCpuModel/CMakeLists.txt
examples/java/surfPlugin/CMakeLists.txt
examples/java/suspend/CMakeLists.txt
examples/java/tracing/CMakeLists.txt
examples/lua/CMakeLists.txt
examples/msg/CMakeLists.txt
examples/msg/actions/CMakeLists.txt
examples/msg/bittorrent/CMakeLists.txt
examples/msg/bittorrent/generate.py
examples/msg/chainsend/CMakeLists.txt
examples/msg/chord/CMakeLists.txt
examples/msg/chord/generate.py
examples/msg/cloud/CMakeLists.txt
examples/msg/energy/consumption/CMakeLists.txt
examples/msg/energy/onoff/CMakeLists.txt
examples/msg/energy/pstate/CMakeLists.txt
examples/msg/exception/CMakeLists.txt
examples/msg/gpu/CMakeLists.txt
examples/msg/gtnets/CMakeLists.txt
examples/msg/icomms/CMakeLists.txt
examples/msg/icomms/peer.c
examples/msg/icomms/peer2.c
examples/msg/icomms/peer3.c
examples/msg/io/CMakeLists.txt
examples/msg/io/io.tesh
examples/msg/io/remote.tesh
examples/msg/io/storage.tesh
examples/msg/kademlia/CMakeLists.txt
examples/msg/kademlia/generate.py
examples/msg/masterslave/CMakeLists.txt
examples/msg/masterslave/masterslave_arg.c
examples/msg/masterslave/masterslave_bypass.c
examples/msg/masterslave/masterslave_cluster.c
examples/msg/masterslave/masterslave_failure.c
examples/msg/masterslave/masterslave_forwarder.c
examples/msg/masterslave/masterslave_mailbox.c
examples/msg/mc/CMakeLists.txt
examples/msg/mc/bugged1.tesh
examples/msg/mc/bugged1_liveness.tesh
examples/msg/mc/bugged1_liveness_sparse.tesh
examples/msg/mc/bugged1_liveness_stack_cleaner
examples/msg/mc/bugged1_liveness_visited.tesh
examples/msg/mc/bugged1_liveness_visited_sparse.tesh
examples/msg/mc/bugged2.tesh
examples/msg/mc/centralized.tesh
examples/msg/migration/CMakeLists.txt
examples/msg/ns3/CMakeLists.txt
examples/msg/parallel_task/CMakeLists.txt
examples/msg/parallel_task/test_ptask.c
examples/msg/pastry/CMakeLists.txt
examples/msg/pmm/CMakeLists.txt
examples/msg/priority/CMakeLists.txt
examples/msg/priority/priority.c
examples/msg/properties/CMakeLists.txt
examples/msg/properties/msg_prop.c
examples/msg/semaphores/CMakeLists.txt
examples/msg/sendrecv/CMakeLists.txt
examples/msg/start_kill_time/CMakeLists.txt
examples/msg/suspend/CMakeLists.txt
examples/msg/token_ring/CMakeLists.txt
examples/msg/token_ring/ring_call.c
examples/msg/token_ring/token_bypass.c
examples/msg/tracing/CMakeLists.txt
examples/platforms/conf/transform_optorsim_platform.pl
examples/platforms/generation_scripts/create_hierarchical_clusters.pl
examples/platforms/generation_scripts/enhancedDTDwithHierarchicalCluster.pl
examples/platforms/generation_scripts/generate_g5k_platform.pl
examples/platforms/generation_scripts/generate_g5k_platform_cabinets.pl
examples/platforms/syscoord/generate_peer_platform.pl
examples/scala/CMakeLists.txt
examples/scala/master_slave_bypass/CMakeLists.txt
examples/scala/master_slave_kill/CMakeLists.txt
examples/scala/masterslave/CMakeLists.txt
examples/simdag/CMakeLists.txt
examples/simdag/dax/CMakeLists.txt
examples/simdag/dax/generate_forkjoin.pl
examples/simdag/dax/generate_strassen.pl
examples/simdag/dot/.gitignore [new file with mode: 0644]
examples/simdag/dot/CMakeLists.txt
examples/simdag/goal/CMakeLists.txt
examples/simdag/io/CMakeLists.txt
examples/simdag/metaxml/CMakeLists.txt
examples/simdag/properties/CMakeLists.txt
examples/simdag/scheduling/CMakeLists.txt
examples/smpi/CMakeLists.txt
examples/smpi/MM/CMakeLists.txt
examples/smpi/energy/CMakeLists.txt
examples/smpi/energy/f77/CMakeLists.txt
examples/smpi/energy/f90/CMakeLists.txt
examples/smpi/mc/.gitignore [new file with mode: 0644]
examples/smpi/mc/bugged1_liveness.c
examples/smpi/mc/non_deterministic.tesh
examples/smpi/mc/only_send_deterministic.c
examples/smpi/mc/only_send_deterministic.tesh
examples/smpi/replay_multiple/CMakeLists.txt
examples/smpi/replay_multiple/replay_multiple.tesh
examples/smpi/smpi_msg_masterslave/CMakeLists.txt
examples/smpi/smpi_msg_masterslave/masterslave_mailbox_smpi.c
examples/xbt/CMakeLists.txt
include/simgrid/modelchecker.h
include/simgrid/msg.h
include/simgrid_config.h.in
include/smpi/smpi.h
include/surf/surfxml_parse.h
include/xbt.h
include/xbt/automaton.h
include/xbt/base.h
include/xbt/config.h
include/xbt/cunit.h
include/xbt/dynar.h
include/xbt/ex.h
include/xbt/file.h [new file with mode: 0644]
include/xbt/log.h
include/xbt/misc.h
include/xbt/str.h
include/xbt/sysdep.h
include/xbt/xbt_os_thread.h
src/bindings/java/MANIFEST.MF.in
src/bindings/java/jmsg_as.c
src/bindings/java/jmsg_comm.c
src/bindings/java/jmsg_host.c
src/bindings/java/jmsg_storage.c
src/bindings/java/jmsg_synchro.c
src/bindings/java/jmsg_task.c
src/bindings/java/org/simgrid/NativeLib.java
src/bindings/java/org/simgrid/msg/Comm.java
src/bindings/java/org/simgrid/msg/File.java
src/bindings/java/org/simgrid/msg/Msg.java
src/bindings/java/org/simgrid/msg/Mutex.java
src/bindings/java/org/simgrid/msg/Process.java
src/bindings/java/org/simgrid/msg/RngStream.java
src/bindings/java/org/simgrid/msg/Semaphore.java
src/bindings/java/org/simgrid/msg/Task.java
src/bindings/java/org/simgrid/surf/SurfJNI.java
src/bindings/java/org/simgrid/trace/Trace.java
src/bindings/java/smx_context_java.c
src/bindings/java/surf.i
src/bindings/lua/lua_state_cloner.c
src/bindings/lua/simgrid_lua.c
src/include/mc/datatypes.h
src/include/mc/mc.h
src/include/simgrid/sg_config.h
src/include/smpi/smpi_interface.h
src/include/surf/maxmin.h
src/include/surf/surf.h
src/instr/instr_private.h
src/mc/AddressSpace.hpp
src/mc/Frame.hpp
src/mc/ModelChecker.cpp
src/mc/ModelChecker.hpp
src/mc/ObjectInformation.hpp
src/mc/PageStore.hpp
src/mc/Process.cpp [moved from src/mc/mc_process.cpp with 87% similarity]
src/mc/Process.hpp [moved from src/mc/mc_process.h with 93% similarity]
src/mc/RegionSnapshot.cpp
src/mc/RegionSnapshot.hpp
src/mc/Type.hpp
src/mc/Variable.hpp
src/mc/mc_base.cpp
src/mc/mc_base.h
src/mc/mc_checkpoint.cpp
src/mc/mc_client.cpp
src/mc/mc_client.h
src/mc/mc_comm_pattern.h
src/mc/mc_compare.cpp
src/mc/mc_config.cpp
src/mc/mc_diff.cpp
src/mc/mc_dwarf.cpp
src/mc/mc_dwarf.hpp [new file with mode: 0644]
src/mc/mc_dwarf_expression.cpp
src/mc/mc_dwarf_tagnames.cpp
src/mc/mc_forward.hpp
src/mc/mc_global.cpp
src/mc/mc_hash.cpp
src/mc/mc_hash.hpp
src/mc/mc_ignore.h
src/mc/mc_liveness.h
src/mc/mc_location.h
src/mc/mc_member.cpp
src/mc/mc_memory_map.h
src/mc/mc_object_info.h
src/mc/mc_page_snapshot.cpp
src/mc/mc_private.h
src/mc/mc_protocol.h
src/mc/mc_record.cpp
src/mc/mc_record.h
src/mc/mc_request.cpp
src/mc/mc_request.h
src/mc/mc_safety.cpp
src/mc/mc_safety.h
src/mc/mc_server.h
src/mc/mc_smx.cpp
src/mc/mc_smx.h
src/mc/mc_snapshot.cpp
src/mc/mc_snapshot.h
src/mc/mc_state.h
src/mc/mc_unw.cpp
src/mc/mc_unw.h
src/mc/mc_visited.cpp
src/mc/mc_xbt.hpp
src/mc/mcer_ignore.cpp
src/mc/mcer_ignore.h
src/mc/memory_map.cpp
src/mc/simgrid_mc.cpp
src/msg/msg_gos.c
src/msg/msg_host.c
src/msg/msg_io.c
src/msg/msg_mailbox.h
src/msg/msg_private.h
src/msg/msg_task.c
src/msg/msg_vm.c
src/portable.h
src/simdag/dax_dtd.h
src/simdag/private.h
src/simdag/sd_daxloader.c
src/simgrid/sg_config.c
src/simgrid/util.hpp
src/simix/popping_accessors.h
src/simix/popping_generated.c
src/simix/popping_private.h
src/simix/simcalls.py
src/simix/smx_context.c
src/simix/smx_context_raw.c
src/simix/smx_deployment.c
src/simix/smx_global.c
src/simix/smx_host_private.h
src/simix/smx_io_private.h
src/simix/smx_network.c
src/simix/smx_network_private.h
src/simix/smx_private.h
src/simix/smx_process_private.h
src/simix/smx_synchro_private.h
src/smpi/colls/gather-mvapich.c
src/smpi/fixsrc.pl
src/smpi/private.h
src/smpi/smpi_global.c
src/smpi/smpi_mpi_dt_private.h
src/smpi/smpi_pmpi.c
src/smpi/smpi_replay.c
src/smpi/smpirun.in
src/surf/cpu_cas01.hpp
src/surf/cpu_ti.cpp
src/surf/cpu_ti.hpp
src/surf/host_clm03.hpp
src/surf/host_interface.hpp
src/surf/host_ptask_L07.cpp
src/surf/host_ptask_L07.hpp
src/surf/maxmin.cpp
src/surf/maxmin_private.hpp
src/surf/network_cm02.hpp
src/surf/network_constant.cpp
src/surf/network_constant.hpp
src/surf/network_ib.hpp
src/surf/network_interface.cpp
src/surf/network_interface.hpp
src/surf/network_ns3.hpp
src/surf/network_smpi.hpp
src/surf/platf_generator_private.h
src/surf/plugins/energy.cpp
src/surf/plugins/energy.hpp
src/surf/storage_interface.cpp
src/surf/storage_interface.hpp
src/surf/storage_n11.cpp
src/surf/storage_n11.hpp
src/surf/surf_interface.cpp
src/surf/surf_interface.hpp
src/surf/surf_private.h
src/surf/surf_routing.hpp
src/surf/surf_routing_cluster.hpp
src/surf/surf_routing_cluster_fat_tree.hpp
src/surf/surf_routing_cluster_torus.hpp
src/surf/surf_routing_dijkstra.hpp
src/surf/surf_routing_floyd.hpp
src/surf/surf_routing_full.hpp
src/surf/surf_routing_generic.hpp
src/surf/surf_routing_none.cpp
src/surf/surf_routing_none.hpp
src/surf/surf_routing_private.hpp
src/surf/surf_routing_vivaldi.hpp
src/surf/surfxml_parse.c
src/surf/trace_mgr_private.h
src/surf/vm_hl13.cpp
src/surf/vm_hl13.hpp
src/surf/vm_interface.hpp
src/win32/config.h [deleted file]
src/xbt/automaton/automaton_lexer.yy.c
src/xbt/automaton/parserPromela.lex
src/xbt/automaton/parserPromela.tab.cacc
src/xbt/automaton/parserPromela.tab.hacc
src/xbt/automaton/parserPromela.yacc
src/xbt/config.c
src/xbt/dict.c
src/xbt/dict_private.h
src/xbt/dynar.c
src/xbt/ex.c
src/xbt/ex_interface.h
src/xbt/graph.c
src/xbt/graph_private.h
src/xbt/graphxml_parse.c
src/xbt/mmalloc/mm_module.c
src/xbt/mmalloc/mmprivate.h
src/xbt/parmap.cpp [moved from src/xbt/parmap.c with 97% similarity]
src/xbt/setset.c
src/xbt/setset_private.h
src/xbt/win32_ucontext.c
src/xbt/xbt_log_appender_file.c
src/xbt/xbt_main.c
src/xbt/xbt_matrix.c
src/xbt/xbt_os_file.c [new file with mode: 0644]
src/xbt/xbt_os_thread.c
src/xbt/xbt_os_time.c
src/xbt/xbt_replay.c
src/xbt/xbt_sg_stubs.c
src/xbt/xbt_sha.c
src/xbt/xbt_str.c
src/xbt_modinter.h
teshsuite/bug-17132/CMakeLists.txt
teshsuite/java/CMakeLists.txt
teshsuite/java/sleep_host_off/CMakeLists.txt
teshsuite/mc/CMakeLists.txt
teshsuite/mc/dwarf/CMakeLists.txt
teshsuite/mc/dwarf/dwarf.cpp
teshsuite/mc/dwarf_expression/CMakeLists.txt
teshsuite/mc/dwarf_expression/dwarf_expression.cpp
teshsuite/mc/mutex_handling.tesh [deleted file]
teshsuite/mc/no_mutex_handling.tesh [deleted file]
teshsuite/mc/replay/CMakeLists.txt
teshsuite/mc/replay/random_bug.tesh
teshsuite/mc/with_mutex_handling.tesh [new file with mode: 0644]
teshsuite/mc/without_mutex_handling.tesh [new file with mode: 0644]
teshsuite/msg/CMakeLists.txt
teshsuite/msg/get_sender/CMakeLists.txt
teshsuite/msg/get_sender/get_sender.c
teshsuite/msg/host_on_off/CMakeLists.txt
teshsuite/msg/host_on_off/host_on_off.c
teshsuite/msg/host_on_off/host_on_off_recv.c
teshsuite/msg/host_on_off_processes/CMakeLists.txt
teshsuite/msg/host_on_off_processes/host_on_off_processes.c
teshsuite/msg/pid/CMakeLists.txt
teshsuite/msg/pid/pid.c
teshsuite/msg/process/CMakeLists.txt
teshsuite/msg/process_join/CMakeLists.txt
teshsuite/msg/storage/CMakeLists.txt
teshsuite/msg/storage/storage_basic.c
teshsuite/msg/task_destroy_cancel/CMakeLists.txt
teshsuite/msg/task_destroy_cancel/task_destroy_cancel.c
teshsuite/msg/trace/CMakeLists.txt
teshsuite/simdag/availability/CMakeLists.txt
teshsuite/simdag/basic/CMakeLists.txt
teshsuite/simdag/incomplete/CMakeLists.txt
teshsuite/simdag/network/CMakeLists.txt
teshsuite/simdag/network/mxn/CMakeLists.txt
teshsuite/simdag/network/p2p/CMakeLists.txt
teshsuite/simdag/network/test_reinit_costs.tesh
teshsuite/simdag/partask/CMakeLists.txt
teshsuite/simdag/platforms/CMakeLists.txt
teshsuite/simix/check_defaults/CMakeLists.txt
teshsuite/simix/stack_overflow/CMakeLists.txt
teshsuite/smpi/CMakeLists.txt
teshsuite/smpi/allgather/CMakeLists.txt
teshsuite/smpi/allgatherv/CMakeLists.txt
teshsuite/smpi/allreduce/CMakeLists.txt
teshsuite/smpi/alltoall/CMakeLists.txt
teshsuite/smpi/alltoallv/CMakeLists.txt
teshsuite/smpi/barrier/CMakeLists.txt
teshsuite/smpi/bcast/CMakeLists.txt
teshsuite/smpi/compute/CMakeLists.txt
teshsuite/smpi/gather/CMakeLists.txt
teshsuite/smpi/hvector/CMakeLists.txt
teshsuite/smpi/indexed/CMakeLists.txt
teshsuite/smpi/isp/umpire/.gitignore [new file with mode: 0644]
teshsuite/smpi/isp/umpire/CMakeLists.txt
teshsuite/smpi/isp/umpire/any_src-can-deadlock10.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-can-deadlock4.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-can-deadlock5.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-can-deadlock6.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-wait-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-waitall-deadlock2.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-waitall-deadlock3.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-waitany-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/any_src-waitany-deadlock2.tesh [deleted file]
teshsuite/smpi/isp/umpire/basic-deadlock-comm_create.tesh [deleted file]
teshsuite/smpi/isp/umpire/basic-deadlock-comm_dup.tesh [deleted file]
teshsuite/smpi/isp/umpire/basic-deadlock-comm_split.tesh [deleted file]
teshsuite/smpi/isp/umpire/basic-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/bcast-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/collective-misorder-allreduce.tesh [deleted file]
teshsuite/smpi/isp/umpire/collective-misorder.tesh [deleted file]
teshsuite/smpi/isp/umpire/complex-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/deadlock-config.tesh [deleted file]
teshsuite/smpi/isp/umpire/finalize-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/irecv-deadlock.tesh [deleted file]
teshsuite/smpi/isp/umpire/no-error.tesh [deleted file]
teshsuite/smpi/isp/umpire/no-error2.tesh [deleted file]
teshsuite/smpi/isp/umpire/no-error3-any_src.tesh [deleted file]
teshsuite/smpi/isp/umpire/no-error3.tesh [deleted file]
teshsuite/smpi/mpich3-test/attr/CMakeLists.txt
teshsuite/smpi/mpich3-test/checktests
teshsuite/smpi/mpich3-test/coll/CMakeLists.txt
teshsuite/smpi/mpich3-test/comm/CMakeLists.txt
teshsuite/smpi/mpich3-test/datatype/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/attr/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/coll/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/comm/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/datatype/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/ext/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/info/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/init/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/pt2pt/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/rma/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/topo/CMakeLists.txt
teshsuite/smpi/mpich3-test/f77/util/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/coll/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/datatype/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/info/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/init/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/pt2pt/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/rma/CMakeLists.txt
teshsuite/smpi/mpich3-test/f90/util/CMakeLists.txt
teshsuite/smpi/mpich3-test/group/CMakeLists.txt
teshsuite/smpi/mpich3-test/info/CMakeLists.txt
teshsuite/smpi/mpich3-test/init/CMakeLists.txt
teshsuite/smpi/mpich3-test/perf/CMakeLists.txt
teshsuite/smpi/mpich3-test/pt2pt/CMakeLists.txt
teshsuite/smpi/mpich3-test/rma/CMakeLists.txt
teshsuite/smpi/mpich3-test/runtests
teshsuite/smpi/mpich3-test/topo/CMakeLists.txt
teshsuite/smpi/pingpong/CMakeLists.txt
teshsuite/smpi/reduce/CMakeLists.txt
teshsuite/smpi/scatter/CMakeLists.txt
teshsuite/smpi/shared/CMakeLists.txt
teshsuite/smpi/struct/CMakeLists.txt
teshsuite/smpi/vector/CMakeLists.txt
teshsuite/surf/CMakeLists.txt
teshsuite/surf/lmm_usage/CMakeLists.txt
teshsuite/surf/maxmin_bench/CMakeLists.txt
teshsuite/surf/surf_usage/CMakeLists.txt
teshsuite/surf/trace_usage/CMakeLists.txt
teshsuite/xbt/graphxml_usage/CMakeLists.txt
teshsuite/xbt/heap_bench/CMakeLists.txt
teshsuite/xbt/log_large/CMakeLists.txt
teshsuite/xbt/log_usage/CMakeLists.txt
teshsuite/xbt/mallocator/CMakeLists.txt
teshsuite/xbt/mmalloc/CMakeLists.txt
teshsuite/xbt/parallel_log/CMakeLists.txt
teshsuite/xbt/parmap_bench/CMakeLists.txt
teshsuite/xbt/parmap_test/CMakeLists.txt
tools/CMakeLists.txt
tools/MSG_visualization/colorize.pl
tools/MSG_visualization/trace2fig.pl
tools/cmake/CTestConfig.cmake
tools/cmake/CompleteInFiles.cmake
tools/cmake/DefinePackages.cmake
tools/cmake/Distrib.cmake
tools/cmake/Documentation.cmake [moved from tools/cmake/GenerateDoc.cmake with 57% similarity]
tools/cmake/GCCFlags.cmake [moved from tools/cmake/Flags.cmake with 56% similarity]
tools/cmake/GenerateDocWin.cmake [deleted file]
tools/cmake/Java.cmake [new file with mode: 0644]
tools/cmake/MakeJava.cmake [deleted file]
tools/cmake/MakeLib.cmake
tools/cmake/MakeLibWin.cmake
tools/cmake/Modules/FindValgrind.cmake
tools/cmake/Option.cmake
tools/cmake/Pipol.cmake [deleted file]
tools/cmake/PrintArgs.cmake
tools/cmake/Scripts/java_bundle.sh [deleted file]
tools/cmake/Tests.cmake [moved from tools/cmake/AddTests.cmake with 92% similarity]
tools/cmake/cross-mingw.cmake [moved from buildtools/Cross/Mingw.cmake with 88% similarity]
tools/cmake/scripts/Diff.pm [moved from tools/cmake/Scripts/Diff.pm with 100% similarity]
tools/cmake/scripts/IPC/Run.pm [new file with mode: 0644]
tools/cmake/scripts/IPC/Run/Debug.pm [new file with mode: 0644]
tools/cmake/scripts/IPC/Run/IO.pm [new file with mode: 0644]
tools/cmake/scripts/IPC/Run/Timer.pm [new file with mode: 0644]
tools/cmake/scripts/IPC/Run/Win32Helper.pm [new file with mode: 0644]
tools/cmake/scripts/IPC/Run/Win32IO.pm [new file with mode: 0644]
tools/cmake/scripts/IPC/Run/Win32Pump.pm [new file with mode: 0644]
tools/cmake/scripts/Makefile.default [moved from tools/cmake/Scripts/Makefile.default with 100% similarity]
tools/cmake/scripts/SimGrid.packproj [moved from tools/cmake/Scripts/SimGrid.packproj with 100% similarity]
tools/cmake/scripts/generate_memcheck_tests.pl [moved from tools/cmake/Scripts/generate_memcheck_tests.pl with 98% similarity]
tools/cmake/scripts/my_valgrind.pl [moved from tools/cmake/Scripts/my_valgrind.pl with 95% similarity]
tools/cmake/scripts/postinstall.sh [moved from tools/cmake/Scripts/postinstall.sh with 100% similarity]
tools/cmake/scripts/preinstall.sh [moved from tools/cmake/Scripts/preinstall.sh with 100% similarity]
tools/cmake/scripts/update_tesh.pl [moved from tools/cmake/Scripts/update_tesh.pl with 91% similarity]
tools/cmake/src/internal_config.h.in
tools/cmake/test_prog/prog_thread_storage.c
tools/doxygen/fig2dev_postprocessor.pl
tools/doxygen/index_create.pl
tools/doxygen/list_routing_models_examples.sh [new file with mode: 0755]
tools/doxygen/xbt_log_extract_hierarchy.pl
tools/generate-dwarf-functions
tools/graphicator/CMakeLists.txt
tools/internal/check_dist_archive.exclude
tools/internal/generate-multi-jar.py
tools/internal/spell_comments.pl
tools/jenkins/DynamicAnalysis.sh [moved from buildtools/jenkins/run_DynamicAnalysis.sh with 79% similarity]
tools/jenkins/build.sh [moved from buildtools/jenkins/build.sh with 90% similarity]
tools/jenkins/ctest2junit.xsl [moved from buildtools/jenkins/ctest2junit.xsl with 100% similarity]
tools/normalize-pointers.py
tools/sg_unit_extractor.pl
tools/stack-cleaner/as
tools/stack-cleaner/clean-stack-filter
tools/stack-cleaner/compiler-wrapper
tools/tesh/CMakeLists.txt
tools/tesh/IO-broken-pipe.tesh
tools/tesh/IO-orders.tesh
tools/tesh/README [deleted file]
tools/tesh/background.tesh
tools/tesh/basic.tesh
tools/tesh/bg-set-signal.tesh
tools/tesh/catch-return.tesh
tools/tesh/catch-signal.tesh
tools/tesh/catch-timeout.tesh
tools/tesh/catch-wrong-output.tesh
tools/tesh/cd.tesh
tools/tesh/colorize.pl
tools/tesh/set-output-ignore.tesh
tools/tesh/set-output-sort-1.tesh [deleted file]
tools/tesh/set-output-sort.tesh
tools/tesh/set-return.tesh
tools/tesh/set-signal.tesh [deleted file]
tools/tesh/set-timeout.tesh
tools/tesh/setenv.tesh
tools/tesh/tesh.1 [deleted file]
tools/tesh/tesh.pl

diff --git a/.gitattributes b/.gitattributes
new file mode 100644 (file)
index 0000000..0f7186c
--- /dev/null
@@ -0,0 +1,3 @@
+.gitattributes export-ignore
+.gitignore export-ignore
+
index f8f1d37..dcc5b7c 100644 (file)
@@ -20,16 +20,17 @@ addons:
       packages:
       - gcc-4.7
       - g++-4.7
-      - clang
+#      - clang
 # Install libboost-chrono1.48-dev to get boost 1.48 on Ubuntu Precise. What we really want is libboost-dev libboost-all-dev
 # Still need sudo for update-alternatives
 before_install:
-   - sudo apt-get update  -qq
-   - sudo apt-get install -y cmake valgrind default-jdk gfortran liblua5.1-dev lua5.1 libboost-chrono1.48-dev
-   - sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-4.7 50
-   - sudo update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-4.7 50
+   - if [ ${TRAVIS_OS_NAME} = 'linux' ] ; then sudo add-apt-repository --yes ppa:kubuntu-ppa/backports ; fi # cmake higher than 2.8.7
+   - if [ ${TRAVIS_OS_NAME} = 'linux' ] ; then sudo apt-get update  -qq ; fi
+   - if [ ${TRAVIS_OS_NAME} = 'linux' ] ; then sudo apt-get install -y cmake valgrind default-jdk gfortran liblua5.1-dev lua5.1 libboost-chrono1.48-dev ; fi
+   - if [ ${TRAVIS_OS_NAME} = 'linux' ] ; then sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-4.7 50 ; fi
+   - if [ ${TRAVIS_OS_NAME} = 'linux' ] ; then sudo update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-4.7 50 ; fi
 script:
-   - cmake -Denable_documentation=OFF -Denable_coverage=OFF -Denable_java=ON -Denable_model-checking=OFF -Denable_lua=ON -Denable_compile_optimizations=ON -Denable_smpi=ON -Denable_smpi_MPICH3_testsuite=ON -Denable_compile_warnings=ON . && make VERBOSE=1 && ctest --output-on-failure --timeout 100
+   - cmake -Denable_documentation=OFF -Denable_coverage=OFF -Denable_java=ON -Denable_model-checking=OFF -Denable_lua=ON -Denable_compile_optimizations=ON -Denable_smpi=ON -Denable_smpi_MPICH3_testsuite=OFF -Denable_compile_warnings=ON . && make VERBOSE=1 && ctest --output-on-failure --timeout 100
 branches:
   only:
      - master
@@ -47,4 +48,3 @@ notifications:
 os:
   - linux
   - osx
-  - windows
index 5194064..68e71c4 100644 (file)
@@ -1,4 +1,6 @@
 cmake_minimum_required(VERSION 2.6)
+# Java requires 2.8.6
+message(STATUS "Cmake version ${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION}")
 
 project(SimGrid C CXX)
 
@@ -13,51 +15,57 @@ endif()
 
 ## 
 ## Check the C/C++ standard that we need
-##   See also tools/cmake/Flags.cmake that sets our paranoid warning flags
-INCLUDE(CheckCCompilerFlag)
-CHECK_C_COMPILER_FLAG(-fstack-cleaner HAVE_C_STACK_CLEANER)
-
-## Request full debugging flags
-set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -g3")
-set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -g3")
-set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -g")
-
-if (CMAKE_COMPILER_IS_GNUCC)
-  if (COMPILER_CXX_VERSION_MAJOR_MINOR STRLESS "4.7")
-    message(FATAL_ERROR
-            "SimGrid needs at least g++ version 4.7 to compile "
-           "(c++11 support of previous versions is too limited).")
+##   See also tools/cmake/GCCFlags.cmake that sets our paranoid warning flags
+if (MSVC)
+  message("-- You are compiling SimGrid with MicroSoft Visual C. Good luck.")
+
+  set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -D_SCL_SECURE_NO_WARNINGS")
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -D_SCL_SECURE_NO_WARNINGS")
+else() # gcc or clang
+  INCLUDE(CheckCCompilerFlag)
+  CHECK_C_COMPILER_FLAG(-fstack-cleaner HAVE_C_STACK_CLEANER)
+
+  ## Request full debugging flags
+  set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -g3")
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -g3")
+  set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -g")
+
+  if (CMAKE_COMPILER_IS_GNUCC)
+    if (COMPILER_CXX_VERSION_MAJOR_MINOR STRLESS "4.7")
+      message(FATAL_ERROR
+              "SimGrid needs at least g++ version 4.7 to compile "
+             "(c++11 support of previous versions is too limited).")
+    endif()
   endif()
-endif()
-
-## We need a decent support of the c++11 standard
-include(CheckCXXCompilerFlag)
-CHECK_CXX_COMPILER_FLAG("-std=gnu++11" COMPILER_SUPPORTS_CXX11)
-if(COMPILER_SUPPORTS_CXX11)
-  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++11")
-else() 
-  message(FATAL_ERROR 
-          "The compiler ${CMAKE_CXX_COMPILER} has no C++11 support. "
-          "Please use a decent C++ compiler.")
-endif()
 
-### And we need C11 standard, too
-include(CheckCCompilerFlag)
-CHECK_C_COMPILER_FLAG("-std=gnu11" COMPILER_SUPPORTS_C11)
-if(COMPILER_SUPPORTS_C11)
-  set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=gnu11")
-else()
-  message(FATAL_ERROR 
-          "The compiler ${CMAKE_C_COMPILER} has no C11 support. "
-          "Please use a decent C compiler "
-          "(note that c++11 support of ${CMAKE_CXX_COMPILER} seems ok).")
-endif()
-if(APPLE AND ("4.6" GREATER COMPILER_C_VERSION_MAJOR_MINOR))
-    ### gcc 4.[1-5] cannot compile ucontext on OSX
-    message(STATUS "Ucontext can't be used with this version of gcc (must be greater than 4.5)")
-    set(HAVE_UCONTEXT_H 0)
-endif()
+  ## We need a decent support of the c++11 standard
+  include(CheckCXXCompilerFlag)
+  CHECK_CXX_COMPILER_FLAG("-std=gnu++11" COMPILER_SUPPORTS_CXX11)
+  if(COMPILER_SUPPORTS_CXX11)
+    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++11")
+  else() 
+    message(FATAL_ERROR 
+            "The compiler ${CMAKE_CXX_COMPILER} has no C++11 support. "
+            "Please use a decent C++ compiler.")
+  endif()
 
+  ### And we need C11 standard, too
+  include(CheckCCompilerFlag)
+  CHECK_C_COMPILER_FLAG("-std=gnu11" COMPILER_SUPPORTS_C11)
+  if(COMPILER_SUPPORTS_C11)
+    set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=gnu11")
+  else()
+    message(FATAL_ERROR 
+            "The compiler ${CMAKE_C_COMPILER} has no C11 support. "
+            "Please use a decent C compiler "
+            "(note that c++11 support of ${CMAKE_CXX_COMPILER} seems ok).")
+  endif()
+  if(APPLE AND ("4.6" GREATER COMPILER_C_VERSION_MAJOR_MINOR))
+      ### gcc 4.[1-5] cannot compile ucontext on OSX
+      message(STATUS "Ucontext can't be used with this version of gcc (must be greater than 4.5)")
+      set(HAVE_UCONTEXT_H 0)
+  endif()
+endif() # NOT MSVC
 
 ### SMPI vs. Fortran
 if ((NOT DEFINED enable_smpi OR enable_smpi) AND NOT APPLE) # smpi is enabled by default
@@ -84,13 +92,6 @@ if ((NOT DEFINED enable_smpi OR enable_smpi) AND NOT APPLE) # smpi is enabled by
   enable_language(Fortran OPTIONAL)
 endif()
 
-if (CMAKE_COMPILER_IS_GNUCC)
-  if(COMPILER_C_VERSION_MAJOR_MINOR STRGREATER "4.8")
-    set (CMAKE_AR gcc-ar)
-    set (CMAKE_RANLIB gcc-ranlib)
-  endif()
-endif()
-
 #-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#
 #     Build the version number      #
 #-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#-#
@@ -98,7 +99,7 @@ endif()
 set(SIMGRID_VERSION_MAJOR "3")
 set(SIMGRID_VERSION_MINOR "12")
 set(SIMGRID_VERSION_PATCH "0")
-set(SIMGRID_VERSION_EXTRA "-devel") # Extra words to add to version string (e.g. -rc1)
+set(SIMGRID_VERSION_EXTRA "-devel") # Extra words to add to version string (e.g. -rc1)
 
 set(SIMGRID_VERSION_DATE  "2015") # Year for copyright information
 
@@ -140,11 +141,6 @@ endif()
 exec_program("${CMAKE_LINKER} --version" OUTPUT_VARIABLE "LINKER_VERSION")
 string(REGEX MATCH "[0-9].[0-9]*" LINKER_VERSION "${LINKER_VERSION}")
 
-string(REGEX MATCH "cl.exe" VBC "${CMAKE_C_COMPILER}")
-if(VBC)
-  message("VB is not yet supported by Simgrid. Proceed with extrem caution")
-endif()
-
 ### Find programs and paths
 FIND_PROGRAM(GCOV_PATH gcov)
 include(FindPerl)
@@ -173,7 +169,6 @@ set(INCLUDES
 if(WIN32)
   set(INCLUDES ${INCLUDES} ${CMAKE_HOME_DIRECTORY}/include/xbt ${CMAKE_HOME_DIRECTORY}/src/xbt) #for win32_ucontext.[ch]
 endif()
-set(CMAKE_SOURCE_DIR ${PROJECT_SOURCE_DIRECTORY})
 
 if(NOT CMAKE_CROSSCOMPILING AND EXISTS /usr/include/)
   set(INCLUDES ${INCLUDES} /usr/include/)
@@ -181,7 +176,11 @@ endif()
 
 ### Check 32bits or 64bits
 INCLUDE (CheckTypeSize)
+CHECK_TYPE_SIZE("int" SIZEOF_INT)
+CHECK_TYPE_SIZE("long" SIZEOF_LONG)
+CHECK_TYPE_SIZE("long long" SIZEOF_LONGLONG)
 CHECK_TYPE_SIZE("void*" SIZEOF_VOIDSTAR)
+message ("   Data model: (int)=${SIZEOF_INT} (long)=${SIZEOF_LONG} (long long)=${SIZEOF_LONGLONG} (void*)=${SIZEOF_VOIDSTAR}")
 IF(SIZEOF_VOIDSTAR EQUAL 4)
   SET(ARCH_32_BITS 1)
 ELSE()
@@ -210,8 +209,6 @@ if(WIN32)
     if(COMPILER_C_MINOR_VERSION)
       # set(__GNUC_MINOR__ ${COMPILER_C_MINOR_VERSION})
     endif()
-  else()
-    message("You REALLY should use MinGW to compile SimGrid on Windows!")
   endif()
 
   set(NSIS_WIN_VERSION $ENV{PROCESSOR_ARCHITEW6432})
@@ -252,8 +249,10 @@ include(${CMAKE_HOME_DIRECTORY}/tools/cmake/DefinePackages.cmake)
 include(${CMAKE_HOME_DIRECTORY}/tools/cmake/MaintainerMode.cmake)
 include(${CMAKE_HOME_DIRECTORY}/tools/cmake/UnitTesting.cmake)
 
-### Setup gcc flags
-include(${CMAKE_HOME_DIRECTORY}/tools/cmake/Flags.cmake)
+### Setup gcc & clang flags
+if (NOT MSVC)
+  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/GCCFlags.cmake)
+endif()
 
 ### Make Libs
 if(NOT WIN32)
@@ -262,28 +261,40 @@ else()
   include(${CMAKE_HOME_DIRECTORY}/tools/cmake/MakeLibWin.cmake)
 endif()
 
-### Make Exes
-include(${CMAKE_HOME_DIRECTORY}/tools/cmake/MakeExe.cmake)
+if(enable_java)
+  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/Java.cmake)
+endif()
 
 ### Make tests
 if(enable_memcheck_xml)
   set(enable_memcheck true)
 endif()
 
-include(${CMAKE_HOME_DIRECTORY}/tools/cmake/AddTests.cmake)
+INCLUDE(CTest)
+ENABLE_TESTING()
+include(${CMAKE_HOME_DIRECTORY}/tools/cmake/Tests.cmake)
 include(${CMAKE_HOME_DIRECTORY}/tools/cmake/CTestConfig.cmake)
 
+### Define subdirectories
+include(${CMAKE_HOME_DIRECTORY}/tools/cmake/MakeExe.cmake)
+
 ### Setup the distrib
 include(${CMAKE_HOME_DIRECTORY}/tools/cmake/Distrib.cmake)
 
-### Pipol compilation
-include(${CMAKE_HOME_DIRECTORY}/tools/cmake/Pipol.cmake)
-
-### Build the doc
+### Build the doc (Windows downloads the doc instead of regenerating)
+#
 if(NOT WIN32)
-  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/GenerateDoc.cmake)
+  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/Documentation.cmake)
 else()
-  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/GenerateDocWin.cmake)
+  find_program(WGET_PROGRAM  NAMES wget)
+  message(STATUS "wget: ${WGET_PROGRAM}")
+  if(WGET_PROGRAM)
+    ADD_CUSTOM_TARGET(simgrid_documentation
+      COMMENT "Downloading the SimGrid documentation..."
+      COMMAND ${WGET_PROGRAM} -r -np -nH -nd http://simgrid.gforge.inria.fr/simgrid/${release_version}/doc/
+      WORKING_DIRECTORY ${CMAKE_HOME_DIRECTORY}/doc/html
+    )
+  endif()
 endif()
 
 ### Print ARGS
index 890a010..76d321e 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,10 +1,15 @@
-SimGrid (3.12) NOT RELEASED; urgency=low
+SimGrid (3.12) stable; urgency=low
+
+ The Facelift Release.
 
  Build System
   * Require g++ v4.7 at least to not speak prehistorical C++.
   * Require Boost 1.48 (for signal2 component).
+  * Java must be version 7 at least when activated.
+  * Builds on Windows again (including Java bindings).
   * Tracing is now always enabled (no way to turn it out)
   * Remove GTNetS. It was not working anyway.
+  * Various cleanups in the cmake scripts.
   * Move headers around to sort them out on installed systems:
     - instr/instr.h  -> simgrid/instr.h
     - instr/jedule/* -> simgrid/jedule
@@ -19,7 +24,7 @@ SimGrid (3.12) NOT RELEASED; urgency=low
    - Sanitize the interface in MSG_task_ module:
      - Merge two functions that were close enough but misleading:
        set_compute_duration(t)      -> set_flops_amount(t)
-       get_remaining_computation(t) -> set_flops_amount(t)
+       get_remaining_computation(t) -> get_flops_amount(t)
      - set_data_size(t) -> set_bytes_amount(t)
        get_data_size(t) -> get_bytes_amount(t)
    - Massive cleanups in the functions related to the energy
@@ -106,13 +111,14 @@ SimGrid (3.12) NOT RELEASED; urgency=low
    - Add a xbt_heap_update function, to avoid costly xbt_heap_remove+xbt_heap_insert use
    - Add a xbt wrapper for simcall_mutex_trylock (asked in [#17878])
    - Add two new log appenders : rollfile and splitfile. Patch by Fabien Chaix.
+   - xbt_dirname and xbt_basename for non-POSIX systems
  MC
   * The model checker now runs as a separate process.
   * The model checker runs must now be launched with the new simgrid-mc program.
   * Record/Replay: the MC can display a textual representation of a path in the
     execution graph. It can then be replayed outside of the model checker.
 
- -- $date Da SimGrid team <simgrid-devel@lists.gforge.inria.fr>
+ -- Mon Oct 12 06:02:41 CEST 2015 Da SimGrid team <simgrid-devel@lists.gforge.inria.fr>
 
 SimGrid (3.11) stable; urgency=low
 
diff --git a/NEWS b/NEWS
index d5075f9..74b0569 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -3,11 +3,13 @@ __   _____ _ __ ___(_) ___  _ __   |___ / / |___ \
 \ \ / / _ \ '__/ __| |/ _ \| '_ \    |_ \ | | __) |
  \ V /  __/ |  \__ \ | (_) | | | |  ___) || |/ __/
   \_/ \___|_|  |___/_|\___/|_| |_| |____(_)_|_____|
+                Oct 12 2015
 
 The Facelift Release. Major changes:
 
  * Many interface glitches addressed, everywhere.
-   - Require g++-4.7 and boost 1.48
+   - Require g++-4.7, Java 7 and boost 1.48
+   - Builds on Linux, OS X, Windows and FreeBSD
    - See ChangeLog for renamed functions and options.
 
  * Energy plugin: major cleanups/rewrites.
diff --git a/TODO b/TODO
index 03e4af8..c3617dd 100644 (file)
--- a/TODO
+++ b/TODO
 ### Ongoing stuff
 ###
 
-* Switch to tesh.pl, and kill the now unused parts of xbt that seem fragile
-
-* Clean up CMake files (may need a full rewrite).
+* Clean up CMake files
    Non exhaustive list of subgoals:
    - Use genuine cmake mechanisms and variables when available,
      instead of reinventing the wheel.
    - Correctly determine system and architecture (e.g. x32).
    - Correctly determine compiler type and version (e.g. clang).
-   - Correctly set compiler flags according to compiler type and version.
-   - Correctly set compiler flags for C++, Java, and Fortran compilers too.
    - Use git to generate the dist archive.  Either use git-archive to
      generate the tarball, or keep using cmake -E tar, but use git-ls-files
      to get the list of files to pack.
 
-* Document host module
-
 * /* FIXME: better place? */
   int vasprintf  (char **ptr, const char *fmt, va_list ap);
   char *bprintf(const char*fmt, ...) _XBT_GNUC_PRINTF(1,2);
 
-###
-### Planned
-###
-
-*
-* XBT
-*****
-
-[errors/exception]
-  * Better split casual errors from programming errors.
-    The first ones should be reported to the user, the second should kill
-    the program (or, yet better, only the msg handler)
-  * Allows the use of an error handler depending on the current module (ie,
-    the same philosophy as log4c using GSL's error functions)
-
-[logs]
-  * Hijack message from a given category to another for a while (to mask
-    initializations, and more)
-  * Allow each actor to have its own setting
-  * more logging appenders (take those from Ralf in l2)
-
-[modules]
-  * Add configuration and dependencies to our module definition
+* Replace XBT with the C++ standard library, once everything is ported
+  to C++
 
-[other modules]
-  * we may need a round-robin database module, and a statistical one
-  * Some of the datacontainer modules seem to overlap. Kill some of them?
+* Some XBT datacontainers seem to overlap. Kill some of them?
     - replace fifo with dynars
     - replace set with SWAG
index 0c55d30..8817dd1 100644 (file)
@@ -1,35 +1,93 @@
 # This file is intended to automatize the testing of SimGrid on
 # Windows using the appveyor.com continuous integration service
 
-os: MinGW
+os: Visual Studio 2015
 version: "{build}"
 clone_depth: 1
 
-platform: 
-  - Win32 # This is Windows 32bits (don't activate since we dont compile properly anyway)
-#  - x64   # This is Windows 64bits
+# scripts that are called at very beginning, before repo cloning
+init:
+- cmake --version
+- msbuild /version
+- git config --global core.longpaths true
+- git config --global core.autocrlf input
 
 environment:
-  BOOST_ROOT: c:\Libraries\boost
-  BOOST_LIBRARYDIR: c:\Libraries\boost\stage\lib
-    
+  global:
+    BOOST_ROOT: c:\Libraries\boost_1_59_0
+    BOOST_LIBRARYDIR: c:\Libraries\boost_1_59_0\stage\lib
+    #  BOOST_ROOT: c:\Libraries\boost
+    #  BOOST_LIBRARYDIR: c:\Libraries\boost\stage\lib
+    TESH_ARGS: C:/projects/simgrid/bin/tesh --setenv srcdir=C:/projects/simgrid/examples/java --setenv classpath=C:/projects/simgrid/examples/java;C:/projects/simgrid/teshsuite/java;C:/projects/simgrid/simgrid.jar --cd C:/projects/simgrid/examples/java
+  matrix:
+    - COMPILER: MinGW-w64
+
+#    - COMPILER: MSVC15
+#      PLATFORM: Win32
+#    - COMPILER: MSVC15
+#      PLATFORM: x64
+      
+install:
+- if [%COMPILER%]==[MinGW]     set PATH=C:\MinGW\bin;%PATH%
+- if [%COMPILER%]==[MinGW]     mingw-get update
+- if [%COMPILER%]==[MinGW]     rename "C:\Program Files (x86)\Git\bin\sh.exe" "sh2.exe"
+- if [%COMPILER%]==[MinGW-w64] set PATH=C:\mingw64\bin;%PATH%
+- if [%COMPILER%]==[MinGW-w64] rename "C:\Program Files (x86)\Git\bin\sh.exe" "sh2.exe"
+- if [%COMPILER%]==[MinGW-w64] appveyor DownloadFile "https://raw.githubusercontent.com/symengine/dependencies/5cff7d1736877336cf9fb58267111beea4fa152f/x86_64-4.9.1-release-posix-seh-rt_v3-rev1.7z" -FileName mw64.7z || appveyor DownloadFile "https://raw.githubusercontent.com/symengine/dependencies/5cff7d1736877336cf9fb58267111beea4fa152f/x86_64-4.9.1-release-posix-seh-rt_v3-rev1.7z" -FileName mw64.7z
+- if [%COMPILER%]==[MinGW-w64] 7z x -oC:\ mw64.7z > NUL
+- if [%COMPILER%]==[MSYS2]     set PATH=C:\msys64\bin,%PATH%
+
 build_script:
-- '"C:\Program Files (x86)\Microsoft Visual Studio 12.0\Common7\Tools\VsDevCmd"'
-- C:\MinGW\msys\1.0\bin\bash -lc "echo \"C:/MinGW /mingw\" > /etc/fstab"
-- C:\MinGW\msys\1.0\bin\bash -lc "printenv"
-- C:\MinGW\msys\1.0\bin\bash -lc "cd /c/projects/simgrid && cmake -G \"MSYS Makefiles\" -DBOOST_ROOT=\"%BOOST_ROOT%\" -DBOOST_LIBRARYDIR=\"%BOOST_LIBRARYDIR%\" -DBoost_USE_STATIC_LIBS=ON -Denable_debug=ON -Denable_documentation=OFF -Denable_coverage=OFF -Denable_tracing=ON -Denable_java=OFF -Denable_model-checking=OFF ."
-- C:\MinGW\msys\1.0\bin\bash -lc "cd /c/projects/simgrid; echo XXX simgrid_config.h; cat include/simgrid_config.h"
-- C:\MinGW\msys\1.0\bin\bash -lc "cd /c/projects/simgrid; echo XXX src/internal_config.h; cat src/internal_config.h"
-#- C:\MinGW\msys\1.0\bin\bash -lc "cd /c/projects/simgrid; echo XXX Internal builtins; gcc -dM -E - < /dev/null"
-- C:\MinGW\msys\1.0\bin\bash -lc "cd /c/projects/simgrid && make VERBOSE=1"
+- if [%COMPILER%]==[MSVC15] if [%PLATFORM%]==[Win32] cmake -G "Visual Studio 14 2015"       -Denable_java=ON -Denable_smpi=OFF -Denable_mallocators=OFF .
+- if [%COMPILER%]==[MSVC15] if [%PLATFORM%]==[x64]   cmake -G "Visual Studio 14 2015 Win64" -Denable_java=ON -Denable_smpi=OFF -Denable_mallocators=OFF .
+- if not [%COMPILER%]==[MSVC15]                      cmake -G "MinGW Makefiles"             -Denable_java=ON -Denable_smpi=OFF -Denable_mallocators=OFF -Denable_lto=OFF .
+- if [%COMPILER%]==[MSVC15]     msbuild ALL_BUILD.vcxproj /verbosity:normal
+- if not [%COMPILER%]==[MSVC15] mingw32-make VERBOSE=1
+- cd C:/projects/simgrid/examples/java && java -classpath ".;../../simgrid.jar" masterslave.Masterslave ../platforms/platform.xml masterslave/masterslaveDeployment.xml || true
+
+
+# I cant use the cmake test because of the following error:
+#   Test project C:/projects/simgrid
+#        Start   1: mc-replay-random-bug
+#   ^CTerminate batch job (Y/N)?
+# How dafuq am I supposed to press N on appveyor?? I tried closing stdin, in vain
+#- bash -c "cd C:/projects/simgrid; exec 0<&-; ctest --output-on-failure" < nul || true
 
 test_script:
-  cmd: ctest -VV
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/async/async.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/bittorrent/bittorrent.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/master_slave_bypass/bypass.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/chord/chord.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/cloud/cloud.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/cloud/migration/migration.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/commTime/commtime.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/kademlia/kademlia.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/master_slave_kill/kill.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/masterslave/masterslave.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/migration/migration.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/mutualExclusion/mutualexclusion.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/pingPong/pingpong.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/priority/priority.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/startKillTime/startKillTime.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/surfCpuModel/surf_cpu_model.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/surfPlugin/surf_plugin.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/reservationSurfPlugin/reservation_surf_plugin.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/suspend/suspend.tesh
+- perl %TESH_ARGS% C:/projects/simgrid/examples/java/tracing/tracingPingPong.tesh
+
+artifacts:
+- path: simgrid.jar
+  name: jarfile
 
 # notifications:
 # - irc: "irc.debian.org#simgrid" # Not implemented by AppVeyor yet :(
 # Some source of inspiration:
+
+# https://github.com/sympy/symengine/blob/master/appveyor.yml <- MS, mingw & mingw64
+
 # https://github.com/dartsim/dart/blob/master/appveyor.yml
 # https://github.com/osmcode/libosmium/blob/master/appveyor.yml
 # https://github.com/polysquare/cmake-unit/blob/master/appveyor.yml
 # https://github.com/openvswitch/ovs/blob/master/appveyor.yml
+
+# https://github.com/behdad/harfbuzz/pull/112/files
\ No newline at end of file
index b160b3f..bd353fa 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2009, 2011, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,7 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 
 sub melange {
     my $tableau=shift;
index f314d9e..fc4e84b 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2011, 2014. The SimGrid Team.
 # All rights reserved.
index e2633d1..9a1f50d 100644 (file)
Binary files a/contrib/psg/tutorial.odt and b/contrib/psg/tutorial.odt differ
index faf141b..df0ef22 100644 (file)
Binary files a/contrib/psg/tutorial.pdf and b/contrib/psg/tutorial.pdf differ
index 505dc70..7dc2fcf 100644 (file)
@@ -644,9 +644,11 @@ WARN_LOGFILE           =
 
 INPUT                  = doxygen/index.doc \
                          doxygen/getting_started.doc \
+                         doxygen/getting_started_index.doc \
                          doxygen/introduction.doc \
                          doxygen/install.doc \
-                         doxygen/use.doc \   
+                         doxygen/examples.doc \   
+                         doxygen/understanding_simgrid.doc \   
                            doxygen/platform.doc \
                            doxygen/deployment.doc \
                            doxygen/options.doc \
@@ -779,7 +781,8 @@ EXCLUDE_SYMBOLS        =
 EXAMPLE_PATH           = ./ \
                          @top_srcdir@/src/surf/ \
                          @top_srcdir@/src/xbt/ \
-                         @top_srcdir@/examples
+                         @top_srcdir@/examples \
+                         @top_srcdir@/doc/example_lists
 
 # If the value of the EXAMPLE_PATH tag contains directories, you can use the
 # EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp
index 17001e6..385846f 100644 (file)
@@ -1,28 +1,35 @@
 <doxygenlayout version="1.0">
   <!-- Navigation index tabs for HTML output -->
   <navindex>
-    <tab type="mainpage" visible="yes" title="" />
-  
-    <tab type="pages" visible="no" title="Table Of Content" intro="Complete pages list">
-      <tab type="pages" visible="yes" title="Table Of Content" intro="Complete pages list"/>
-    </tab>
-    <tab type="namespaces" visible="no" title="">
-      <tab type="namespaces" visible="yes" title="" intro=""/>
-      <tab type="namespacemembers" visible="yes" title="" intro=""/>
-    </tab>
-    <tab type="classes" visible="no" title="">
-      <tab type="classes" visible="yes" title="" intro=""/>
-      <tab type="classindex" visible="$ALPHABETICAL_INDEX" title=""/> 
-      <tab type="hierarchy" visible="yes" title="" intro=""/>
-      <tab type="classmembers" visible="yes" title="" intro=""/>
+    <tab type="usergroup" visible="yes" title="Getting started" intro="Getting started" url="@ref getting_started">
+      <tab type="user" visible="yes" url="@ref getting_started" title="What to read" />
+      <tab type="user" visible="yes" url="@ref install" title="Installing SimGrid" />
+      <tab type="user" visible="yes" url="@ref help" title="Getting help" />
     </tab>
-    <tab type="files" visible="no" title="">
-      <tab type="files" visible="yes" title="" intro=""/>
-      <tab type="globals" visible="yes" title="" intro=""/>
-    </tab>
-    <tab type="modules" visible="no" title="" intro="">
-      <tab type="modules" visible="yes" title="APIs Reference"
-           intro="Here is the hierarchical view of all SimGrid modules. You can reduce the amount of detail with the 'detail level' setting, on the right."/>
+    <tab type="mainpage" visible="yes" title="SimGrid User Documentation" />
+  
+    <!--<tab type="pages" visible="yes" title="Table Of Content" intro="Complete pages list">-->
+      <!--<tab type="pages" visible="yes" title="Table Of Content" intro="Complete pages list"/>-->
+    <!--</tab>-->
+    <tab type="usergroup" visible="yes" title="Technical documentation" intro="Technical documentation">
+      <tab type="namespaces" visible="no" title="">
+        <tab type="namespaces" visible="yes" title="" intro=""/>
+        <tab type="namespacemembers" visible="yes" title="" intro=""/>
+      </tab>
+      <tab type="classes" visible="no" title="">
+        <tab type="classes" visible="yes" title="" intro=""/>
+        <tab type="classindex" visible="$ALPHABETICAL_INDEX" title=""/> 
+        <tab type="hierarchy" visible="yes" title="" intro=""/>
+        <tab type="classmembers" visible="yes" title="" intro=""/>
+      </tab>
+      <tab type="files" visible="no" title="">
+        <tab type="files" visible="yes" title="" intro=""/>
+        <tab type="globals" visible="yes" title="" intro=""/>
+      </tab>
+      <tab type="modules" visible="no" title="" intro="">
+        <tab type="modules" visible="yes" title="APIs Reference"
+             intro="Here is the hierarchical view of all SimGrid modules. You can reduce the amount of detail with the 'detail level' setting, on the right."/>
+      </tab>
     </tab>
   </navindex>
 
index 614110f..1ca3d42 100644 (file)
@@ -8,7 +8,6 @@ tutorials.
 
 - @subpage bindings
 - @subpage pls
-- @subpage internals
-- @subpage contributing
+- @subpage tracing
 
-*/
\ No newline at end of file
+*/
index 6068893..1439a60 100644 (file)
@@ -1,45 +1,67 @@
-/*! \page deployment Deployment Description
+/*! \page deployment Step 3: Deploy the simulation
 
 \section dep_over Overview
 
-When using SimGrid, you basically need your user code, a platform description, and something allowing to map your (simulated) process on  your (simulated) platform. This is what deployment file is all about. Note that you can bypass the file stuff and code it directly in your user code, if you want to.
-
-
-\section dep_ex An example
-So deployment file just consists of saying which
-process runs where and which arguments it should take as input, the easier way to
-understand how to write it is just to take a look at the examples. Here is an example of it:
-
-\verbatim
-<?xml version='1.0'?>
-<!DOCTYPE platform SYSTEM "http://simgrid.gforge.inria.fr/simgrid.dtd">
-<platform version="3">
-  <!-- The master process (with some arguments) -->
-  <process host="Tremblay" function="master">
-     <argument value="20"/>       <!-- Number of tasks -->
-     <argument value="50000000"/>  <!-- Computation size of tasks -->
-     <argument value="1000000"/>   <!-- Communication size of tasks -->
-     <argument value="Jupiter"/>  <!-- First slave -->
-     <argument value="Fafard"/>   <!-- Second slave -->
-     <argument value="Ginette"/>  <!-- Third slave -->
-     <argument value="Bourassa"/> <!-- Last slave -->
-     <argument value="Tremblay"/> <!-- Me! I can work too! -->
-  </process>
-  <!-- The slave processes (with no argument) -->
-  <process host="Tremblay" function="slave"/>
-  <process host="Jupiter" function="slave"/>
-  <process host="Fafard" function="slave"/>
-  <process host="Ginette" function="slave"/>
-  <process host="Bourassa" function="slave"/>
-</platform>
-\endverbatim
-
-\section process_tag Process
-There are optional attributes to the process tag, here is a list of all attributes of process: 
-
-\li <b>host (mandatory)</b>: the host on which the function will be executed.  
-\li <b>process (mandatory)</b>: the process function that will be executed on that host. You can deploy as many process as you want on the same host. 
-\li <b>start_time</b>: the (simulated) time when the function will start. Default is zero.
-\li <b>kill_time</b>: the  (simulated) time when the function will stop. Default is when it's actually finishing.
+When you want to simulate the behavior of your code with SimGrid, you need
+to tell SimGrid exactly what code (that you wrote) is supposed to be run by which host - so you need to assign
+processes/functions to hosts. The hosts in question here are the hosts of your platform model; see Section \ref platform for details on how to set one up.
+
+This assignment of the form \c code -> \c host is what the deployment file is all about, which will
+be discussed briefly here.
+
+\note 
+    You can bypass the deployment file by hardcoding it in your user code, at least when you're using
+    MSG.
+
+The deployment file looks just like a \ref platform "platform" file, except that in
+this case, only two different tags are used: \c process and \c argument, whereas
+the latter is just used to supply additional configuration options to the process; the
+order in which the \c argument tags are given is important and depends on the application.
+
+### The process tag ###
+
+#### Attribute list ####
+
+%As already written above, the \c process tag is the tag that defines which host
+executes which function (from your application). Hence, the \c host and \c function
+attributes are mandatory; however, there are some optional attributes to the process tag. Here is a list of all attributes of this tag:
+
+| Attribute name  | Mandatory | Values                 | Description                                                                                                               |
+| --------------- | --------- | ---------------------- | -----------                                                                                                               |
+| host            | yes       | String                 | Describes which host will be used to run this process. The host must be defined in the platform file!                     |
+| function        | yes       | String                 | Name of a function that will be executed on this host; this function is written in userland code, for instance, C code. Valid values are functions that were registered by MSG_function_register() |
+| start_time      | no        | int (Default: -1.0)    | The simulated time when this function will start to be computed.                                                          |
+| kill_time       | no        | int (Default: -1.0)    | The simulated time when this function will end to be computed. By default, it stops only when it's done.                  |
+| on_failure      | no        | DIE\|RESTART (Default: "DIE")   | What should be done when the process fails.                  |
+
+#### An example ####
+
+A complete example including a \ref MSG_ext_ms_application "deployment file" can be found 
+in the Section \ref MSG_ex_basics "MSG basics".
+
+See also files such as \c examples/msg/masterslave/deployment_masterslave.xml.
+
+### The argument tag ###
+
+This tag must always be contained by a \c process tag - it doesn't make sense
+without it.
+
+The way this works is that the order of arguments must be pre-defined <i>by the user</i>:
+It is totally up to you what <i>your</i> code expects as arguments and in which
+order. The arguments will be passed to your code (that is: to the function 
+executed by this process) in the order you declare them.
+
+#### Attribute list ####
+
+| Attribute name  | Mandatory | Values                 | Description                                                                                                               |
+| --------------- | --------- | ---------------------- | -----------                                                                                                               |
+| value           | yes       | String                 | Contains the value for this parameter |
+
+#### An example ####
+
+A complete example including a \ref MSG_ext_ms_application "deployment file" can be found 
+in the Section \ref MSG_ex_basics "MSG basics".
+
+See also files such as \c examples/msg/masterslave/deployment_masterslave.xml.
 
 */
similarity index 73%
rename from doc/doxygen/use.doc
rename to doc/doxygen/examples.doc
index 38b7a48..ef4a8ae 100644 (file)
@@ -1,29 +1,26 @@
-/*! \page use Using SimGrid
+/*! \page examples SimGrid Examples
 
-This page is under work -- sorry for the inconvinience (FIXME).
+\note 
+  This page is under work -- sorry for the inconvenience (FIXME).
 
-- @subpage platform
-- @subpage deployment
-- @subpage tracing
-- @subpage options
-- @subpage help
+- @ref help
 
 \tableofcontents
 
 SimGrid comes with many examples provided in the examples/ directory.
-Those examples are described in section \ref MSG_examples . Those
+Those examples are described in section \ref MSG_examples. Those
 examples are commented and should be easy to understand. for a first
 step into SimGrid we also provide some more detailed examples in the
 sections below. 
 
 \htmlonly
-You should also check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a generic tutorial about using SimGrid. 
+You should also check our online <a href="http://simgrid.gforge.inria.fr/documentation.html"> tutorial section</a> that contains a generic tutorial about using SimGrid. 
 \endhtmlonly
 
 \section using_msg Using MSG
 
 \htmlonly
-You should also check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a dedicated tutorial. 
+You should also check our online <a href="http://simgrid.gforge.inria.fr/documentation.html"> tutorial section</a> that contains a dedicated tutorial. 
 \endhtmlonly
 
 Here are some examples on how to use MSG, the most used API.
@@ -61,9 +58,9 @@ an external description of the deployment.
 
 \paragraph MSG_ext_icomms_Sender Sender function
 
-The sender send to a receiver an asynchronous message with the function "MSG_task_isend()". Cause this function is non-blocking
-we have to make "MSG_comm_test()" to know   if the communication is finished for finally destroy it with function "MSG_comm_destroy()".
-It also available to "make MSG_comm_wait()" which make both of them.
+A host can send an an asynchronous message with \c MSG_task_isend(). %As this function is non-blocking,
+we have to call \c MSG_comm_test() to know if the communication has finished and finally destroy it with a call to \c MSG_comm_destroy().
+It is also possible to call \c MSG_comm_wait() which, is provides a shortcut.
 
   C style arguments (argc/argv) are interpreted as:
    - the number of tasks to distribute
@@ -80,8 +77,8 @@ It also available to "make MSG_comm_wait()" which make both of them.
 
 \paragraph MSG_ext_icomms_Receiver Receiver function
 
-This function executes tasks when it receives them. As the receiving is asynchronous we have to test the communication to know
-if it is completed or not with "MSG_comm_test()" or wait for the completion "MSG_comm_wait()".
+This function executes tasks when it receives them. %As the receiving is asynchronous we have to test the communication to know
+if it is completed or not with \c MSG_comm_test() or wait for the completion \c MSG_comm_wait().
 
   C style arguments (argc/argv) are interpreted as:
    - the id to use for received the communication.
@@ -169,7 +166,7 @@ and an external description of the deployment.
 
 \paragraph MSG_ext_ms_master Master code
 
-This function has to be assigned to a msg_process_t that will behave as
+This function has to be assigned to a #msg_process_t that will behave as
 the master. It should not be called directly but either given as a
 parameter to #MSG_process_create() or registered as a public function
 through #MSG_function_register() and then automatically assigned to a
@@ -188,7 +185,7 @@ Tasks are dumbly sent in a round-robin style.
 \paragraph MSG_ext_ms_slave Slave code
 
 This function has to be assigned to a #msg_process_t that has to behave
-as a slave. Just like the master fuction (described in \ref
+as a slave. Just like the master function (described in \ref
 MSG_ext_ms_master), it should not be called directly.
 
 This function keeps waiting for tasks and executes them as it receives them.
@@ -201,10 +198,10 @@ This function has to be assigned to a #msg_process_t that has to behave
 as a forwarder. Just like the master function (described in \ref
 MSG_ext_ms_master), it should not be called directly.
 
-C style arguments (argc/argv) are interpreted as a list of host that
+C style arguments (argc/argv) are interpreted as a list of hosts that
 will accept those tasks.
 
-This function keeps waiting for tasks and dispathes them to its slaves.
+This function keeps waiting for tasks and dispatches them to its slaves.
 
 \until end_of_forwarder
 
@@ -232,30 +229,15 @@ This initializes MSG, runs a simulation, and free all data-structures created by
 
 \subsubsection MSG_ext_ms_helping Helping files
 
-\paragraph MSG_ext_ms_application Example of application file
+\paragraph MSG_ext_ms_application Example of a deployment file
 
-\include msg/masterslave/deployment_masterslave.xml
+The following listing can be found in \c examples/msg/masterslave/deployment_masterslave_forwarder.xml:
 
-\paragraph MSG_ext_ms_platform Example of platform file
+\include msg/masterslave/deployment_masterslave_forwarder.xml
 
-\include platforms/small_platform.xml
-
-\section using_smpi Using SMPI
-You should check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a dedicated tutorial. 
-
-\section using_MC Using Model Checking
-You should check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a dedicated tutorial. 
-
-\section using_trace Using Trace
-Check out the \ref tracing section.
+\paragraph MSG_ext_ms_platform Example of a platform file
 
-You should check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a dedicated tutorial. 
-
-\section using_simdag Using SimDag
-You should check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a dedicated tutorial. 
-
-\section using_simix Using SIMIX
-You should check our online <a href="http://simgrid.gforge.inria.fr/tutorials.html"> tutorial section</a> that contains a dedicated tutorial. 
+\include platforms/small_platform.xml
 
 */
 
index b4ad556..6b86b9b 100644 (file)
@@ -1,9 +1,71 @@
-/*! @page getting_started SimGrid in 30mn
+/*! @page getting_started Getting started with SimGrid!
 
-This page does not exist yet. In the meanwhile, please refer to the
-<a href="http://simgrid.gforge.inria.fr/tutorials.html">tutorials</a>
-on the project web page, looking for the 
-<a href="http://simgrid.gforge.inria.fr/tutorials/simgrid-use-101.pdf">SimGrid
-User 101</a> tutorial.
+\tableofcontents
 
-*/
\ No newline at end of file
+Welcome to SimGrid's documentation! %As you may know, SimGrid is (actively
+developed) research software and contains many features. This documentation is
+\c "work in progress" (and we need the community's help to improve this
+documentation! If you're ready to step up and help us, see Section \ref
+contributing "Contributing"), but many features are already well described.
+
+%As for many projects, our documentation consists mostly of documentation
+for \ref gs_new_users "new" and \ref gs_experienced_users "experienced" users, but
+we also have several pages plus a technical documentation; in addition to that, we have
+also written many \ref gs_examples "examples" that you can easily adapt to your
+own needs. This page gives you a brief overview of available resources.
+
+\section gs_introduction Introduction, Installation and how we can help
+
+| Document name     | Description                                       |
+| ----------------- | ------------------------------------------------- |
+| \ref introduction | Introduces the user to basic features of SimGrid. |
+| \ref install      | Explains how SimGrid can be installed; this covers Windows as well as Linux; plus, it shows how to install from a package or how to install from source. |
+| \ref FAQ          | Our FAQ                                           |
+| \ref help         | There are many ways to find answers to your questions. This document lists them. |
+
+\section gs_new_users Documentation for new users
+
+| Document name     | Description                                       |
+| ----------------- | ------------------------------------------------- |
+| \ref introduction | Introduces the user to basic features of SimGrid. |
+| \ref install      | Explains how SimGrid can be installed; this covers Windows as well as Linux; plus, it shows how to install from a package or how to install from source. |
+| [Tutorials](http://simgrid.gforge.inria.fr/tutorials.html) | These tutorials cover most of the basics and might be valuable for what you want to do, especially the [SimGrid User 101](http://simgrid.gforge.inria.fr/tutorials/simgrid-use-101.pdf). |
+| \ref MSG_examples | This document explains several tests that we wrote for MSG; these tests are working simulations and you may learn something from looking at them. |
+
+In order to actually use SimGrid, three steps are necessary:
+
+\li \ref platform
+\li \ref options
+\li \ref deployment
+
+\section gs_experienced_users Documentation for experienced users
+
+| Document name     | Description                                       |
+| ----------------- | ------------------------------------------------- |
+| \ref tracing      | Shows how the behavior of a program can be written to a file so that it can be analyzed. |
+| \ref bindings     | SimGrid supports many different bindings for languages such as Lua, Ruby, Java, ... You can run your simulations with those! |
+| \ref pls          | Although SimGrid is not a packet level simulator, it does have bindings to two such simulators. |
+| \ref internals    | If you want to contribute or obtain a deeper understanding of SimGrid, this is the right location. |
+
+\section gs_examples Examples shipped with SimGrid
+
+SimGrid ships with many examples. You can find them in the folder
+\c examples/. Especially when you're looking for examples on how to
+use a specific XML-tag, this will prove valuable, as you can easily
+search through all the files with tools like \c grep.
+
+
+Here is the output of a quick search for examples for \ref pf_trace "trace_connect":
+
+\verbatim
+% grep -R -i -n --include="*.xml" "trace_connect" .
+./simdag/two_hosts.xml:22:   <trace_connect trace="Tremblay_power" element="Tremblay" kind="POWER"/>
+./platforms/two_hosts_platform_with_availability_included.xml:24:<trace_connect kind="POWER" trace="A" element="Cpu A"/>
+./platforms/two_hosts_platform_with_availability_included.xml:25:<trace_connect kind="HOST_AVAIL" trace="A_failure" element="Cpu A"/>
+./platforms/two_hosts_platform_with_availability_included.xml:26:<trace_connect kind="POWER" trace="B" element="Cpu B"/>
+\endverbatim
+
+\note
+    There's also a Section on \ref MSG_examples "examples for MSG".
+
+*/
diff --git a/doc/doxygen/getting_started_index.doc b/doc/doxygen/getting_started_index.doc
new file mode 100644 (file)
index 0000000..fd207e8
--- /dev/null
@@ -0,0 +1,13 @@
+/*! 
+@page getting_started_index Getting Started 
+
+- @subpage getting_started
+- @subpage install
+    - @ref help
+- @subpage advanced
+  - @ref bindings
+  - @ref pls
+  - @ref tracing
+  - @ref contributing
+
+*/
index dc21012..34b8dcc 100644 (file)
@@ -5,19 +5,20 @@ reading the current documentation and studying the provided examples.
 But if a question remains, don't hesitate to ask to the community. You
 have several ways of doing so:
 
- - Ask your question to the
-   <a href="mailto:simgrid-user@lists.gforge.inria.fr">User Mailing list</a>
- - Asking your quetion on Stack Overflow is also a good idea, as this
-   site is very well indexed. We answer questions there too (don't
-   forget to use the SimGrid tag in your question so that we can see
-   it), and they remain usable for the next users.
+ - Ask your question on the
+   <a href="mailto:simgrid-user@lists.gforge.inria.fr">User Mailing list</a> (to subscribe, visit the [webinterface](http://lists.gforge.inria.fr/mailman/listinfo/simgrid-user));
+   you can also check out [our archives](http://lists.gforge.inria.fr/pipermail/simgrid-user/).
  - If your question is about the internals and not about using
    SimGrid, you may prefer to send your question to the 
    <a href="mailto:simgrid-devel@lists.gforge.inria.fr">Developers Mailing list</a>
  - Join us on IRC and ask your question directly on the chanel \#simgrid at
-   irc.debian.org. Be warned that even if many people are connected to
+   \b irc.debian.org. Be warned that even if many people are connected to
    the chanel, they may be doing some useful stuff instead of lurking
-   on IRC. So don't be surprised if you don't get an answer in the
+   on IRC. So don't be surprised if you don't get an answer in the same
    second, and turn to the mailing lists if nobody seems to be there.
+ - Asking your question on Stack Overflow is also a good idea, as this
+   site is very well indexed. We answer questions there too (don't
+   forget to use the SimGrid tag in your question so that we can see
+   it), and they remain usable for the next users.
 
-*/
\ No newline at end of file
+*/
index 2c4802d..e84a1a2 100644 (file)
@@ -1,5 +1,5 @@
 /*!  
-@mainpage SimGrid Documentation
+@mainpage SimGrid User Documentation
 
 @image html simgrid_logo_2011.png  "Versatile Simulation of Distributed Systems, for Grids, Clouds, P2P and HPC systems"
 @image latex simgrid_logo_2011.png "Versatile Simulation of Distributed Systems, for Grids, Clouds, P2P and HPC systems"
 <tr><td width="50%">
 @endhtmlonly
 
-- @subpage getting_started
 - @subpage introduction
-- @subpage install
-- @subpage use
-  - @ref platform
-  - @ref deployment
-  - @ref tracing
-  - @ref options
-  - @ref help
+- @subpage platform
+- @subpage options
+- @subpage deployment
+- @subpage examples
 - @subpage advanced
   - @ref bindings
   - @ref pls
+  - @ref tracing
   - @ref contributing
-  - @ref internals
 - @subpage FAQ
+- @subpage internals
+- @subpage contributing
 
 @htmlonly
 </td><td width="50%" align="center">
index e043df1..bfcf981 100644 (file)
@@ -207,7 +207,7 @@ machine.
 
 Then you have to request cmake to run your test when "ctest" is
 launched. For that, you have to modify source
-<project/directory>/tools/cmake/AddTests.cmake. Make sure to pick
+<project/directory>/tools/cmake/Tests.cmake. Make sure to pick
 a wise name for your test. It is often useful to check a category of
 tests together. The only way to do so in ctest is to use the -R
 argument that specifies a regular expression that the test names must
index 338e022..7095bed 100644 (file)
@@ -193,12 +193,11 @@ distribution. It will also be copied automatically to the documentation.
 
 \section inside_doxygen_website Working on the website
 
-Actually, the website is very different from doxygen. It uses a tool
-called jekyll to turn markup-formated text into nice static web pages.
-Jekyll is less annoying than doxygen since it's written in a scripting
-language: you can dynamically add (or change) parts of the tool to
-make it fit your needs. Get the sources, and start improving the
-website now (there is a README in the repo with more details).
+Our website is generated/exported via [orgmode](http://www.orgmode.org), a tool that we use to facilitate our reproducible research.
+
+Get the sources, and start improving the
+website now! (There is a README in the repo with more details, 
+but it might be outdated. Contact us if you really want to help.)
 
 @verbatim
 git clone git://scm.gforge.inria.fr/simgrid/website.git
index bb37b1d..a88c6b5 100644 (file)
@@ -4,23 +4,27 @@
 \tableofcontents
 
 \section simgrid_dev_guide_model How to add a new model in surf?
-The figure below show the architecture of the SURF layer. This layer is composed
-of different kind of models representing the differents systems we want to
-modelize (i.e.cpu, network, storage, workstation, virtual machine).
+The figure below shows the architecture of the SURF layer. This layer is composed
+of different kinds of models representing the different systems we want to
+model (i.e., cpu, network, storage, workstation, virtual machine).
 
 A model in simgrid is composed of three classes: Model, Resource and Action
-(surf_interface.hpp).
+(\ref SURF_interface "surf_interface.hpp").
 
 \image html surf++.png
 \image latex surf++.pdf "surf++" width=\textwidth
 
 Actually there are five kind of models: CpuModel, NetworkModel, WorkstationModel,
 WorkstationVMModel and StorageModel. For each kind of model, there is an
-interface (e.g.: cpu_interface.hpp) and some implementations (e.g.: cpu_cas01.hpp,
+interface (e.g.: \ref SURF_cpu_interface "cpu_interface.hpp") and some implementations (e.g.: cpu_cas01.hpp,
 cpu_ti.hpp).
 
-init function:
-void surf_cpu_model_init_Cas01()
+The CPU model Cas01, for instance, is initialized by the function
+    void surf_cpu_model_init_Cas01()
+
+The different network models that are offered by simgrid are stored in the array
+that is defined as follows:
+
 s_surf_model_description_t surf_network_model_description[] = {
 
 \subsection simgrid_dev_guide_model_implem How to add a new model implementation in surf?
index c5f74fe..30e96a8 100644 (file)
@@ -1,4 +1,4 @@
-/*! @page internals SimGrid internals
+/*! @page internals SimGrid Developer Guide
 
 This page does not exist yet, sorry. We are currently refurbishing the
 user documentation -- the internal documentation will follow (FIXME).
@@ -89,4 +89,4 @@ See the \ref XBT_API section for more details.
 \subsection ug_lucas_layer Tracing simulation
 Finally, a transversal module allows you to trace your simulation. More documentation in the section \ref TRACE_doc
 
-*/
\ No newline at end of file
+*/
index 3db49d5..5d7bfe5 100644 (file)
@@ -1,5 +1,6 @@
 /*! @page introduction Introduction to SimGrid
 
+
 [SimGrid](http://simgrid.gforge.inria.fr/) is a toolkit
 that provides core functionalities for the simulation of distributed
 applications in heterogeneous distributed environments.
@@ -9,7 +10,9 @@ distributed and parallel application scheduling on distributed computing
 platforms ranging from simple network of workstations to Computational
 Grids.
 
-# Scenario
+\tableofcontents
+
+\section  Scenario
 The goal of this practical session is to illustrate various usage of
 the MSG interface. To this end we will use the following simple setting:
 
@@ -92,7 +95,10 @@ usage over a long period of time.
 
 ![Test](./sc3-description.png)
 
-# Prerequisites
+\section Prerequisites
+
+Of course, you need to install SimGrid before taking this tutorial.
+Please refer to the relevant Section: \ref install.
 
 ## Tutorials
 
@@ -103,23 +109,7 @@ provided by the [online documentation][fn:4] and by several tutorials:
 - http://simgrid.gforge.inria.fr/tutorials/simgrid-tracing-101.pdf
 - http://simgrid.gforge.inria.fr/tutorials/simgrid-platf-101.pdf
 
-## Installing SimGrid
-
-In case you're using [Debian](https://www.debian.org) or a derivate,
-such as Ubuntu or Mint, you can install SimGrid by using the provided
-packages:
-
-    sudo apt-get install libsimgrid-dev
-
-This tutorial requires simgrid 3.8 at least so you may need to get
-the [debian packages](http://packages.debian.org/libsimgrid-dev).
-
-Please note that your distribution may ship with an old version of
-SimGrid; you may want to use [a newer release](https://gforge.inria.fr/frs/?group_id=12)
-or even [clone our git repository](https://gforge.inria.fr/frs/?group_id=12)
-(a [GitHub mirror](https://github.com/mquinson/simgrid) is also available).
-
-# Recommended Steps
+\section intro_recommendation Recommended Steps
 
 ## Installing Viva
 
@@ -159,7 +149,9 @@ This software provides a [Gantt-chart visualization][fn:6].
 sudo apt-get install vite
 ~~~~
 
-# Let's get Started
+\section intro_start Let's get started
+
+\anchor intro_setup
 ## Setting up and Compiling
 
 The corresponding archive with all source files and platform files
@@ -352,7 +344,7 @@ tasks processed). These debug messages can be activated as follows:
 ## Using the Tracing Mechanism
 
 SimGrid can trace all resource consumption and the outcome can be
-displayed with viva as illustrated in the section "Setting up and Compiling". However, when several
+displayed with viva as illustrated in the section \ref intro_setup. However, when several
 masters are deployed, it is hard to understand what happens.
 
 ~~~~{.xml}
@@ -435,7 +427,7 @@ void xbt_dynar_shift(xbt_dynar_t const dynar, void *const dst);
 unsigned long xbt_dynar_length(const xbt_dynar_t dynar);
 ~~~~
 
-As you will soon realize, with such simple mechanisms, simple
+%As you will soon realize, with such simple mechanisms, simple
 deadlocks will soon appear. They can easily be removed with a
 simple polling mechanism, hence the need for the following
 [function][fn:7]:
@@ -444,7 +436,7 @@ simple polling mechanism, hence the need for the following
 msg_error_t MSG_process_sleep(double nb_sec);
 ~~~~
 
-As you should quickly realize, on the simple previous example, it
+%As you should quickly realize, on the simple previous example, it
 will double the throughput of the platform but will be quite
 ineffective when input size of the tasks is not negligible anymore.
 
@@ -459,8 +451,8 @@ From this, many things can easily be added. For example, you could:
 ## Using More Elaborate Platforms
 
 SimGrid offers a rather powerful platform modeling mechanism. The
-`src/platform/` repository comprises a variety of platform ranging
-from simple ones to quite elaborated ones. Associated to a good
+`src/examples/platforms/` repository comprises a variety of platforms ranging
+from simple to elaborate. Associated to a good
 visualization tool to ensure your simulation is meaningful, they
 can allow you to study to which extent your algorithm scales...
 
@@ -468,7 +460,7 @@ What is the largest number of tasks requiring 50e6 flops and 1e5
 bytes that you manage to distribute and process in one hour on
 `g5k.xml` (you should use `deployment_general.xml`)?
 
-# Points to improve for the next time
+\section intro_todo TODO: Points to improve for the next time
 
 - Propose equivalent exercises and skeleton in java.
 - Propose a virtualbox image with everything (simgrid, paje, viva,
index 0474d17..65b0f29 100644 (file)
@@ -502,7 +502,7 @@ Example: adding a "pair" version of the Alltoall collective.
 
  - To register the new version of the algorithm, simply add a line to the corresponding macro in src/smpi/colls/cools.h ( add a "COLL_APPLY(action, COLL_ALLTOALL_SIG, pair)" to the COLL_ALLTOALLS macro ). The algorithm should now be compiled and be selected when using --cfg=smpi/alltoall:pair at runtime.
 
- - To add a test for the algorithm inside Simgrid's test suite, juste add the new algorithm name in the ALLTOALL_COLL list found inside buildtools/cmake/AddTests.cmake . When running ctest, a test for the new algorithm should be generated and executed. If it does not pass, please check your code or contact us.
+ - To add a test for the algorithm inside Simgrid's test suite, juste add the new algorithm name in the ALLTOALL_COLL list found inside buildtools/cmake/Tests.cmake . When running ctest, a test for the new algorithm should be generated and executed. If it does not pass, please check your code or contact us.
 
  - Feel free to push this new algorithm to the SMPI repository using Git.
 
index cf5fad5..686f202 100644 (file)
@@ -4,6 +4,7 @@
     - Portability support
       - \ref XBT_syscall
       - \ref XBT_str
+      - \ref XBT_file
     - Grounding features
       - \ref XBT_ex
       - \ref XBT_log
index 328e201..539c43f 100644 (file)
@@ -1,4 +1,4 @@
-/*! \page options Simgrid options and configurations
+/*! \page options Step 2: Configure SimGrid
 
 A number of options can be given at runtime to change the default
 SimGrid behavior. For a complete list of all configuration options
@@ -9,6 +9,8 @@ report so that we can fix it. Note that some of the options presented
 here may not be available in your simulators, depending on the
 @ref install_src_config "compile-time options" that you used.
 
+\tableofcontents
+
 \section options_using Passing configuration options to the simulators
 
 There is several way to pass configuration options to the simulators.
@@ -92,7 +94,7 @@ described in
   - \b LV08 (default one): Realistic network analytic model
     (slow-start modeled by multiplying latency by 10.4, bandwidth by
     .92; bottleneck sharing uses a payload of S=8775 for evaluating RTT)
-  - \b Constant: Simplistic network model where all communication
+  - \anchor options_model_select_network_constant \b Constant: Simplistic network model where all communication
     take a constant time (one second). This model provides the lowest
     realism, but is (marginally) faster.
   - \b SMPI: Realistic network model specifically tailored for HPC
@@ -271,7 +273,8 @@ Note that with the default host model this option is activated by default.
 \subsubsection options_model_network_coord Coordinated-based network models
 
 When you want to use network coordinates, as it happens when you use
-an \<AS\> in your platform file with \c Vivaldi as a routing, you must
+an \<AS\> in your platform file with \c Vivaldi as a routing (see also
+Section \ref pf_routing_model_vivaldi "Vivaldi Routing Model"), you must
 set the \b network/coordinates to \c yes so that all mandatory
 initialization are done in the simulator.
 
@@ -316,10 +319,10 @@ in NS3. The only valid values (enforced on the SimGrid side) are
 
 \section options_modelchecking Configuring the Model-Checking
 
-To enable the experimental SimGrid model-checking support the program should
-be executed with the command line argument
+To enable the SimGrid model-checking support the program should
+be executed using the simgrid-mc wrapper:
 \verbatim
---cfg=model-check:1
+simgrid-mc ./my_program
 \endverbatim
 
 Safety properties are expressed as assertions using the function
@@ -338,10 +341,6 @@ ltl2ba program.
 --cfg=model-check/property:<filename>
 \endverbatim
 
-Of course, specifying a liveness property enables the model-checking
-so that you don't have to give <tt>--cfg=model-check:1</tt> in
-addition.
-
 \subsection options_modelchecking_steps Going for stateful verification
 
 By default, the system is backtracked to its initial state to explore
@@ -359,9 +358,6 @@ setting for your specific system.
 --cfg=model-check/checkpoint:1
 \endverbatim
 
-Of course, specifying this option enables the model-checking so that
-you don't have to give <tt>--cfg=model-check:1</tt> in addition.
-
 \subsection options_modelchecking_reduction Specifying the kind of reduction
 
 The main issue when using the model-checking is the state space
@@ -382,10 +378,6 @@ For now, this configuration variable can take 2 values:
  * dpor: Apply Dynamic Partial Ordering Reduction. Only valid if you
    verify local safety properties.
 
-Of course, specifying a reduction technique enables the model-checking
-so that you don't have to give <tt>--cfg=model-check:1</tt> in
-addition.
-
 \subsection options_modelchecking_visited model-check/visited, Cycle detection
 
 In order to detect cycles, the model-checker needs to check if a new explored
@@ -756,7 +748,7 @@ be simulated using SMPI by calling internal smpi_execute*() functions.
 
 To disable the benchmarking/simulation of computation in the simulated
 application, the variable \b
-smpi/simulation_computation should be set to no
+smpi/simulate_computation should be set to no
 
 \subsection options_model_smpi_bw_factor smpi/bw_factor: Bandwidth factors
 
@@ -784,10 +776,10 @@ Here, MAX_BANDWIDTH denotes the bandwidth of the link.
 
 \b Default: 0 (false)
 
-Most of the time, you run MPI code through SMPI to compute the time it
-would take to run it on a platform that you don't have. But since the
+Most of the time, you run MPI code with SMPI to compute the time it
+would take to run it on a platform. But since the
 code is run through the \c smpirun script, you don't have any control
-on the launcher code, making difficult to report the simulated time
+on the launcher code, making it difficult to report the simulated time
 when the simulation ends. If you set the \b smpi/display_timing item
 to 1, \c smpirun will display this information when the simulation ends. \verbatim
 Simulation time: 1e3 seconds.
@@ -1126,7 +1118,7 @@ silently overflow on other parts of the memory.
 - \c smpi/privatize_global_variables: \ref options_smpi_global
 - \c smpi/running_power: \ref options_smpi_bench
 - \c smpi/send_is_detached_thresh: \ref options_model_smpi_detached
-- \c smpi/simulation_computation: \ref options_smpi_bench
+- \c smpi/simulate_computation: \ref options_smpi_bench
 - \c smpi/test: \ref options_model_smpi_test
 - \c smpi/use_shared_malloc: \ref options_model_smpi_use_shared_malloc
 - \c smpi/wtime: \ref options_model_smpi_wtime
index ad27aa9..365daca 100644 (file)
@@ -1,4 +1,4 @@
-/*! \page platform Platform Description
+/*! \page platform Step 1: %Model the underlying platform
 
 @tableofcontents
 
@@ -120,7 +120,7 @@ There are three tags to use:
 
 Here is an illustration of these concepts:
 
-![An illustration of an AS hierarchy. Here, AS1 contains 5 other AS' who in turn may contain other AS' as well.](AS_hierarchy.png)
+![An illustration of an AS hierarchy. Here, AS1 contains 5 other ASes who in turn may contain other ASes as well.](AS_hierarchy.png)
  Circles represent processing units and squares represent network routers. Bold
     lines represent communication links. AS2 models the core of a national
     network interconnecting a small flat cluster (AS4) and a larger
@@ -248,6 +248,7 @@ It is also possible to specify whether the host is up or down by setting the
 
 If you want this host to be unavailable, simply substitute ON with OFF.
 
+\anchor pf_host_churn
 ### Expressing churn ###
 
 To express the fact that a host can change state over time (as in P2P
@@ -340,7 +341,7 @@ bb_lat          | no        | int    | Latency for backbone (if any). See <b>lin
 bb_sharing_policy | no      | string | Sharing policy for the backbone (if any). See <b>link</b> section for syntax/details.
 availability_file | no      | string | Allows you to use a file as input for availability. Similar to <b>hosts</b> attribute.
 state_file        | no      | string | Allows you to use a file as input for states.  Similar to <b>hosts</b> attribute.
-loopback_bw       | no      | int    | Bandwidth for loopback (if any). See <b>link</b> section for syntax/details. If loopback_bw and loopback_lat (see below) attributes are omitted, no loopback link is created and all intra-node communication will use the main network link of the node. Loopback link is a \ref sharing_policy_fatpipe "\b FATPIPE".
+loopback_bw       | no      | int    | Bandwidth for loopback (if any). See <b>link</b> section for syntax/details. If loopback_bw and loopback_lat (see below) attributes are omitted, no loopback link is created and all intra-node communication will use the main network link of the node. Loopback link is a \ref pf_sharing_policy_fatpipe "\b FATPIPE".
 loopback_lat      | no      | int    | Latency for loopback (if any). See <b>link</b> section for syntax/details. See loopback_bw for more info.
 topology          | no      | FLAT\|TORUS\|FAT_TREE (default: FLAT) | Network topology to use. SimGrid currently supports FLAT (with or without backbone, as described before), <a href="http://en.wikipedia.org/wiki/Torus_interconnect">TORUS </a> and FAT_TREE attributes for this tag.
 topo_parameters   | no      | string | Specific parameters to pass for the topology defined in the topology tag. For torus networks, comma-separated list of the number of nodes in each dimension of the torus. For fat trees, refer to \ref AsClusterFatTree "AsClusterFatTree documentation".
@@ -405,7 +406,7 @@ lat             | yes       | int    | Latency for the links between nodes and b
 \note
     Please note that as of now, it is impossible to change attributes such as,
     amount of cores (always set to 1), the initial state of hosts/links
-    (always set to ON), the sharing policy of the links (always set to \ref sharing_policy_fullduplex "FULLDUPLEX").
+    (always set to ON), the sharing policy of the links (always set to \ref pf_sharing_policy_fullduplex "FULLDUPLEX").
 
 #### Example ####
 
@@ -494,10 +495,10 @@ several other tags that are available only in certain contexts.
     latency, and that can be shared according to TCP way to share this
     bandwidth.
 \remark
-  The concept of links in SimGrid may not be intuitive, as links are not limited
-  to connecting (exactly) two entities; in fact, you can have more than two equipments
-  connected to it. (In graph theoretical terms: A link in SimGrid is not an edge,
-  but a hyperedge)
+  The concept of links in SimGrid may not be intuitive, as links are not
+  limited to connecting (exactly) two entities; in fact, you can have more than
+  two equipments connected to it. (In graph theoretical terms: A link in
+  SimGrid is not an edge, but a hyperedge)
 
 2. ``<router/>``: Represents an entity that a message can be routed
     to, but that is unable to execute any code. In SimGrid, routers have also
@@ -543,7 +544,7 @@ Attribute name  | Mandatory | Values | Description
 id              | yes       | string | The identifier of the link to be used when referring to it.
 bandwidth       | yes       | int    | Maximum bandwidth for this link, given in bytes/s
 latency         | no        | double (default: 0.0) | Latency for this link.
-sharing_policy  | no        | \ref sharing_policy_shared "SHARED"\|\ref sharing_policy_fatpipe "FATPIPE"\|\ref sharing_policy_fullduplex "FULLDUPLEX" (default: SHARED) | Sharing policy for the link.
+sharing_policy  | no        | \ref sharing_policy_shared "SHARED"\|\ref pf_sharing_policy_fatpipe "FATPIPE"\|\ref pf_sharing_policy_fullduplex "FULLDUPLEX" (default: SHARED) | Sharing policy for the link.
 state           | no        | ON\|OFF (default: ON) | Allows you to to turn this link on or off (working / not working)
 bandwidth_file  | no        | string | Allows you to use a file as input for bandwidth.
 latency_file    | no        | string | Allows you to use a file as input for latency.
@@ -583,7 +584,7 @@ By default a network link is \b SHARED, i.e., if two or more data flows go
 through a link, the bandwidth is shared fairly among all data flows. This
 is similar to the sharing policy TCP uses.
 
-\anchor sharing_policy_fatpipe
+\anchor pf_sharing_policy_fatpipe
 On the other hand, if a link is defined as a \b FATPIPE,
 each flow going through this link will be provided with the complete bandwidth,
 i.e., no sharing occurs and the bandwidth is only limiting each flow individually.
@@ -594,7 +595,7 @@ is ``number_of_flows*bandwidth``, with at most ``bandwidth`` being available per
 Using the FATPIPE mode allows to model backbones that won't affect performance
 (except latency).
 
-\anchor sharing_policy_fullduplex
+\anchor pf_sharing_policy_fullduplex
 The last mode available is \b FULLDUPLEX. This means that SimGrid will
 automatically generate two links (one carrying the suffix _UP and the other the
 suffix _DOWN) for each ``<link>`` tag. This models situations when the direction
@@ -682,16 +683,14 @@ kicks in. It then loops back, starting at 100µs (the initial value) for one sec
 
 #### The ``<prop/>`` tag ####
 
-Similar to ``\<host\>``, the link may also contain the ``<prop/>`` tag; see the host
+Similar to the ``<host>`` tag, a link may also contain the ``<prop/>`` tag; see the host
 documentation (Section \ref pf_host) for an example.
 
 
-TODO
-
 \subsubsection pf_backbone <backbone/>
 
 \note
-  This tag is <b>only available</b> when the containing AS uses the "Cluster" mode!
+  This tag is <b>only available</b> when the containing AS uses the "Cluster" routing mode!
 
 Using this tag, you can designate an already existing link to be a backbone.
 
@@ -702,22 +701,36 @@ id              | yes       | string | Name of the link that is supposed to act
 \subsection pf_storage Storage
 
 \note
-  This is a prototype version that should evolve quickly, this
-  is just some doc valuable only at the time of writing this doc
+  This is a prototype version that should evolve quickly, hence this
+  is just some doc valuable only at the time of writing.
   This section describes the storage management under SimGrid ; nowadays
   it's only usable with MSG. It relies basically on linux-like concepts.
   You also may want to have a look to its corresponding section in \ref
-  msg_file_management ; functions access are organized as a POSIX-like
+  msg_file_management ; access functions are organized as a POSIX-like
   interface.
 
-\subsubsection pf_sto_conc Storage Main concepts
-Basically there are 3 different entities available in SimGrid that
-can be used to model storages:
+\subsubsection pf_sto_conc Storage - Main Concepts
+
+The storage facilities implemented in SimGrid help to model (and account for) 
+storage devices, such as tapes, hard-drives, CD or DVD devices etc. 
+A typical situation is depicted in the figure below:
+
+\image html ./webcruft/storage_sample_scenario.png
+\image latex ./webcruft/storage_sample_scenario.png "storage_sample_scenario" width=\textwidth
+
+In this figure, two hosts called Bob and Alice are interconnected via a network
+and each host is physically attached to a disk; it is not only possible for each host to
+mount the disk they are attached to directly, but they can also mount disks
+that are in a remote location. In this example, Bob mounts Alice's disk remotely
+and accesses the storage via the network.
+
+SimGrid provides 3 different entities that can be used to model setups
+that include storage facilities:
 
 Entity name     | Description
 --------------- | -----------
-\ref pf_storage_entity_storage_type "storage_type"    | Defines a template for a particular kind of storage (such as a hard-drive) and specifies important features of the storage, such as capacity, performance (read/write), content, ... Different models of hard-drives use different storage_types (because the difference between an SSD and an HDD does matter), as they differ in some specifications (e.g., different size or read/write performance).
-\ref pf_storage_entity_storage "storage"        | Defines an actual instance of a storage (disk, RAM, ...); uses a ``storage_type`` template (see line above) so that you don't need to re-specify the same details over and over again.
+\ref pf_storage_entity_storage_type "storage_type"    | Defines a template for a particular kind of storage (such as a hard-drive) and specifies important features of the storage, such as capacity, performance (read/write), contents, ... Different models of hard-drives use different storage_types (because the difference between an SSD and an HDD does matter), as they differ in some specifications (e.g., different sizes or read/write performance).
+\ref pf_storage_entity_storage "storage"        | Defines an actual instance of a storage type (disk, RAM, ...); uses a ``storage_type`` template (see line above) so that you don't need to re-specify the same details over and over again.
 \ref pf_storage_entity_mount "mount"          | Must be wrapped by a \ref pf_host tag; declares which storage(s) this host has mounted and where (i.e., the mountpoint).
 
 
@@ -725,7 +738,7 @@ Entity name     | Description
 ### %Storage Content File ###
 
 In order to assess exactly how much time is spent reading from the storage,
-SimGrid needs to know what is stored in the storage device (identified by distinct (file-)name, like in a file system)
+SimGrid needs to know what is stored on the storage device (identified by distinct (file-)name, like in a file system)
 and what size this content has.
 
 \note
@@ -734,9 +747,9 @@ and what size this content has.
     storage changes, only the internal SimGrid data structures change.
 
 \anchor pf_storage_content_file_structure
-#### Structure of a %Storage File ####
+#### Structure of a %Storage Content File ####
 
-Here is an excerpt from two storage file; if you want to see the whole file, check
+Here is an excerpt from two storage content file; if you want to see the whole file, check
 the file ``examples/platforms/content/storage_content.txt`` that comes with the
 SimGrid source code.
 
@@ -779,7 +792,7 @@ If you want to generate a storage content file based on your own filesystem (or
 try running this command (works only on unix systems):
 
 \verbatim
-find /path/you/want -type f -exec ls -l {} \; 2>/dev/null > ./content.txt
+find . -type f -exec ls -1s --block=1 {} \; 2>/dev/null | awk '{ print $2 " " $1}' > ./content.txt
 \endverbatim
 
 \subsubsection pf_storage_entities The Storage Entities
@@ -833,7 +846,7 @@ Attribute name | Mandatory | Values | Description
 -------------- | --------- | ------ | -----------
 id             | yes       | string | Identifier of this ``storage``; used when referring to it
 typeId         | yes       | string | Here you need to refer to an already existing \ref pf_storage_entity_storage_type "\<storage_type\>"; the storage entity defined by this tag will then inherit the properties defined there.
-attach         | yes       | string | Name of a host (see Section \ref pf_host) that this storage is <i>physically</i> attached to (e.g., a harddrive in a computer)
+attach         | yes       | string | Name of a host (see Section \ref pf_host) to which this storage is <i>physically</i> attached to (e.g., a hard drive in a computer)
 content        | no        | string | When specified, overwrites the content attribute of \ref pf_storage_entity_storage_type "\<storage_type\>"
 content_type   | no        | string | When specified, overwrites the content_type attribute of \ref pf_storage_entity_storage_type "\<storage_type\>"
 
@@ -852,7 +865,7 @@ of type "single_HDD" (shown as an example of \ref pf_storage_entity_storage_type
 to a host called "bob" (the definition of this host is omitted here).
 
 The second storage is called "Disk2", is still of the same type as Disk1 but
-now specifies a new content file (so the content will be different from Disk1)
+now specifies a new content file (so the contents will be different from Disk1)
 and the filesystem uses the windows style; finally, it is attached to a second host,
 called alice (which is again not defined here).
 
@@ -897,7 +910,7 @@ Here is a simple example, taken from the file ``examples/platform/storage.xml``:
 This example is quite interesting, as the same device, called "Disk2", is mounted by
 two hosts at the same time! Note, however, that the host called ``alice`` is actually
 attached to this storage, as can be seen in the \ref pf_storage_entity_storage "&lt;storage&gt;"
-tag. This means that ``denise`` must access this storage via network, but SimGrid automatically takes
+tag. This means that ``denise`` must access this storage through the network, but SimGrid automatically takes
 care of that for you.
 
 Furthermore, this example shows that ``denise`` has mounted two storages with different
@@ -910,6 +923,10 @@ required.
     for instance, a USB stick is attached to one and only one machine (where it's plugged-in)
     but it can only be mounted on others, as mounted storage can also be a remote location.
 
+###### Example files #####
+
+\verbinclude example_filelist_xmltag_mount
+
 \anchor pf_storage_entity_mstorage
 #### &lt;mstorage&gt; ####
 \note
@@ -935,7 +952,7 @@ available in the directory ``examples/msg/io/`` useful.
 \subsubsection pf_storage_examples_modelling Modelling different situations
 
 The storage functionality of SimGrid is type-agnostic, that is, the implementation
-does not presume any type of storagei, such as HDDs/SSDs, RAM,
+does not presume any type of storage, such as HDDs/SSDs, RAM,
 CD/DVD devices, USB sticks etc.
 
 This allows the user to apply the simulator for a wide variety of scenarios; one
@@ -984,81 +1001,85 @@ because the computer designated to be the destination of that message
 is not responding.
 
 We also chose to use shortest paths algorithms in order to emulate
-routing. Doing so is consistent with the reality: RIP, OSPF, BGP are
-all calculating shortest paths. They have some convergence time, but
-at the end, so when the platform is stable (and this should be the
-moment you want to simulate something using SimGrid) your packets will
-follow the shortest paths.
+routing. Doing so is consistent with the reality: [RIP](https://en.wikipedia.org/wiki/Routing_Information_Protocol),
+[OSPF](https://en.wikipedia.org/wiki/Open_Shortest_Path_First), [BGP](https://en.wikipedia.org/wiki/Border_Gateway_Protocol)
+are all calculating shortest paths. They do require some time to converge, but
+eventually, when the routing tables have stabilized, your packets will follow
+the shortest paths.
 
 \subsection pf_rm Routing models
 
-Within each AS, you have to define a routing model to use. You have
-basically 3 main kind of routing models :
-
-\li Shortest-path based models: you let SimGrid calculates shortest
-    paths and manage it. Behaves more or less as most real life
-    routing.
-\li Manually-entered route models: you'll have to define all routes
-    manually by yourself into the platform description file.
-    Consistent with some manually managed real life routing.
-\li Simple/fast models: those models offers fast, low memory routing
-    algorithms. You should consider to use it if you can make some
-    assumptions about your AS. Routing in this case is more or less
-    ignored
+For each AS, you must define explicitly which routing model will
+be used. There are 3 different categories for routing models:
+
+1. \ref pf_routing_model_shortest_path "Shortest-path" based models: SimGrid calculates shortest
+   paths and manages them. Behaves more or less like most real life
+   routing mechanisms.
+2. \ref pf_routing_model_manual "Manually-entered" route models: you have to define all routes
+   manually in the platform description file; this can become
+   tedious very quickly, as it is very verbose.
+   Consistent with some manually managed real life routing.
+3. \ref pf_routing_model_simple "Simple/fast models": those models offer fast, low memory routing
+   algorithms. You should consider to use this type of model if 
+   you can make some assumptions about your AS. 
+   Routing in this case is more or less ignored.
 
 \subsubsection pf_raf The router affair
 
-Expressing routers becomes mandatory when using shortest-path based
+Using routers becomes mandatory when using shortest-path based
 models or when using the bindings to the ns-3 packet-level
 simulator instead of the native analytical network model implemented
 in SimGrid.
 
-For graph-based shortest path algorithms, routers are mandatory,
-because both algorithms need a graph, and so we need to have source
-and destination for each edge.
-
-Routers are naturally an important concept in ns-3 since the
-way they run the packet routing algorithms is actually simulated.
-Instead, the SimGrid’s analytical models aggregate the routing time
-with the transfer time. Rebuilding a graph representation only from
-the route information turns to be a very difficult task, because of
-the missing information about how routes intersect. That is why we
-introduced a \<router\> tag, which is simply used to express these
-intersection points. The only attribute accepted by this tag an id. It
-is important to understand that the \<router\> tag is only used to
-provide topological information.
-
-To express those topological information, some <b>route</b> have to be
-defined saying which link is between which routers. Description or the
-route syntax is given below, as well as example for the different
-models.
-
-\subsubsection pf_rm_sh Shortest-path based models
-
-Here is the complete list of such models, that computes routes using
-classic shortest-paths algorithms. How to choose the best suited
-algorithm is discussed later in the section devoted to it.
-
-\li <b>Floyd</b>: Floyd routing data. Pre-calculates all routes once.
-\li <b>Dijkstra</b>: Dijkstra routing data ,calculating routes when
-    necessary.
-\li <b>DijkstraCache</b>: Dijkstra routing data. Handle some cache for
-    already calculated routes.
-
-All those shortest-path models are instanciated the same way. Here are
-some example of it:
-
-Floyd example :
+For graph-based shortest path algorithms, routers are mandatory, because these
+algorithms require a graph as input and so we need to have source and
+destination for each edge.
+
+Routers are naturally an important concept ns-3 since the
+way routers run the packet routing algorithms is actually simulated.
+SimGrid's analytical models however simply aggregate the routing time
+with the transfer time. 
+
+So why did we incorporate routers in SimGrid? Rebuilding a graph representation
+only from the route information turns out to be a very difficult task, because
+of the missing information about how routes intersect. That is why we
+introduced routers, which are simply used to express these intersection points.
+It is important to understand that routers are only used to provide topological
+information.
+
+To express this topological information, a <b>route</b> has to be
+defined in order to declare which link is connected to a router. 
+
+
+\subsubsection pf_routing_model_shortest_path Shortest-path based models
+
+The following table shows all the models that compute routes using
+shortest-paths algorithms are currently available in SimGrid. More detail on how
+to choose the best routing model is given in the Section called \"\ref pf_routing_howto_choose_wisely\".
+
+| Name                                                | Description                                                                |
+| --------------------------------------------------- | -------------------------------------------------------------------------- |
+| \ref pf_routing_model_floyd "Floyd"                 | Floyd routing data. Pre-calculates all routes once                         |
+| \ref pf_routing_model_dijkstra "Dijkstra"           | Dijkstra routing data. Calculates routes only when needed                  |
+| \ref pf_routing_model_dijkstracache "DijkstraCache" | Dijkstra routing data. Handles some cache for already calculated routes.   |
+
+All those shortest-path models are instanciated in the same way and are
+completely interchangeable. Here are some examples:
+
+\anchor pf_routing_model_floyd
+### Floyd ###
+
+Floyd example:
 \verbatim
 <AS  id="AS0"  routing="Floyd">
 
   <cluster id="my_cluster_1" prefix="c-" suffix=""
-               radical="0-1"   power="1000000000"    bw="125000000"     lat="5E-5"
-        router_id="router1"/>
+           radical="0-1" power="1000000000" bw="125000000" lat="5E-5"
+           router_id="router1"/>
 
- <AS id="AS1" routing="None">
 <AS id="AS1" routing="None">
     <host id="host1" power="1000000000"/>
- </AS>
 </AS>
 
   <link id="link1" bandwidth="100000" latency="0.01"/>
 
@@ -1074,6 +1095,23 @@ Floyd example :
 ASroute given at the end gives a topological information: link1 is
 between router1 and host1.
 
+#### Example platform files ####
+
+This is an automatically generated list of example files that use the Floyd
+routing model (the path is given relative to SimGrid's source directory)
+
+\verbinclude example_filelist_routing_floyd
+
+\anchor pf_routing_model_dijkstra
+### Dijkstra ###
+
+#### Example platform files ####
+
+This is an automatically generated list of example files that use the Dijkstra
+routing model (the path is given relative to SimGrid's source directory)
+
+\verbinclude example_filelist_routing_dijkstra
+
 Dijsktra example :
 \verbatim
  <AS id="AS_2" routing="Dijsktra">
@@ -1094,7 +1132,10 @@ Dijsktra example :
   </AS>
 \endverbatim
 
-DijsktraCache example :
+\anchor pf_routing_model_dijkstracache
+### DijkstraCache ###
+
+DijsktraCache example:
 \verbatim
 <AS id="AS_2" routing="DijsktraCache">
      <host id="AS_2_host1" power="1000000000"/>
@@ -1102,9 +1143,24 @@ DijsktraCache example :
 (platform unchanged compared to upper example)
 \endverbatim
 
-\subsubsection pf_rm_me Manually-entered route models
+#### Example platform files ####
 
-\li <b>Full</b>: You have to enter all necessary routes manually
+This is an automatically generated list of example files that use the DijkstraCache
+routing model (the path is given relative to SimGrid's source directory):
+
+Editor's note: At the time of writing, no platform file used this routing model - so
+if there are no example files listed here, this is likely to be correct.
+
+\verbinclude example_filelist_routing_dijkstra_cache
+
+\subsubsection pf_routing_model_manual Manually-entered route models
+
+| Name                               | Description                                                                    |
+| ---------------------------------- | ------------------------------------------------------------------------------ |
+| \ref pf_routing_model_full "Full"  | You have to enter all necessary routers manually; that is, every single route. This may consume a lot of memory when the XML is parsed and might be tedious to write; i.e., this is only recommended (if at all) for small platforms. |
+
+\anchor pf_routing_model_full
+### Full ###
 
 Full example :
 \verbatim
@@ -1116,31 +1172,87 @@ Full example :
  </AS>
 \endverbatim
 
-\subsubsection pf_rm_sf Simple/fast models
+#### Example platform files ####
 
-\li <b>None</b>: No routing (Unless you know what you are doing, avoid
-using this mode in combination with a non Constant network model).
-None Example :
-\verbatim
-<AS id="exitAS"  routing="None">
-       <router id="exit_gateway"/>
-</AS>\endverbatim
+This is an automatically generated list of example files that use the Full
+routing model (the path is given relative to SimGrid's source directory):
+
+\verbinclude example_filelist_routing_full
+
+\subsubsection pf_routing_model_simple Simple/fast models
+
+| Name                                     | Description                                                                                                                         |
+| ---------------------------------------- | ------------------------------------------------------------------------------                                                      |
+| \ref pf_routing_model_cluster "Cluster"  | This is specific to the \ref pf_cluster "&lt;cluster/&gt;" tag and should not be used by the user, as several assumptions are made. |
+| \ref pf_routing_model_none    "None"     | No routing at all. Unless you know what you're doing, avoid using this mode in combination with a non-constant network model.       |
+| \ref pf_routing_model_vivaldi "Vivaldi"  | Perfect when you want to use coordinates. Also see the corresponding \ref pf_P2P_tags "P2P section" below.                          |
+
+\anchor pf_routing_model_cluster
+### Cluster ###
+
+\note
+ In this mode, the \ref pf_cabinet "&lt;cabinet/&gt;" tag is available.
+
+#### Example platform files ####
+
+This is an automatically generated list of example files that use the Cluster
+routing model (the path is given relative to SimGrid's source directory):
+
+\verbinclude example_filelist_routing_cluster
+
+\anchor pf_routing_model_none
+### None ###
+
+This model does exactly what it's name advertises: Nothing. There is no routing
+available within this model and if you try to communicate within the AS that
+uses this model, SimGrid will fail unless you have explicitly activated the
+\ref options_model_select_network_constant "Constant Network Model" (this model charges
+the same for every single communication). It should
+be noted, however, that you can still attach an \ref pf_routing_tag_asroute "ASroute",
+as is demonstrated in the example below:
+
+\verbinclude platforms/cluster_and_one_host.xml
+
+#### Example platform files ####
+
+This is an automatically generated list of example files that use the None
+routing model (the path is given relative to SimGrid's source directory):
+
+\verbinclude example_filelist_routing_none
+
+
+\anchor pf_routing_model_vivaldi
+### Vivaldi ###
+
+For more information on how to use the [Vivaldi Coordinates](https://en.wikipedia.org/wiki/Vivaldi_coordinates),
+see also Section \ref pf_P2P_tags "P2P tags".
+
+For documentation on how to activate this model (as some initialization must be done
+in the simulator), see Section \ref options_model_network_coord "Activating Coordinate Based Routing".
+
+Note that it is possible to combine the Vivaldi routing model with other routing models;
+an example can be found in the file \c examples/platforms/cloud.xml. This
+examples models an AS using Vivaldi that contains other ASes that use different
+routing models.
+
+#### Example platform files ####
+
+This is an automatically generated list of example files that use the None
+routing model (the path is given relative to SimGrid's source directory):
+
+\verbinclude example_filelist_routing_vivaldi
 
-\li <b>Vivaldi</b>: Vivaldi routing, so when you want to use
-    coordinates. See the corresponding section P2P below for details.
-\li <b>Cluster</b>: Cluster routing, specific to cluster tag, should
-    not be used, except internally.
 
 \subsection ps_dec Defining routes
 
-The principle of route definition is the same for the 4 available tags
-for doing it. Those for tags are:
+There are currently four different ways to define routes: 
 
-\li <b>route</b>: to define route between host/router
-\li <b>ASroute</b>: to define route between AS
-\li <b>bypassRoute</b>: to bypass normal routes as calculated by the
-    network model between host/router
-\li <b>bypassASroute</b>: same as bypassRoute, but for AS
+| Name                                              | Description                                                                         |
+| ------------------------------------------------- | ----------------------------------------------------------------------------------- |
+| \ref pf_routing_tag_route "route"                 | Used to define route between host/router                                            |
+| \ref pf_routing_tag_asroute "ASroute"             | Used to define route between different AS                                           |
+| \ref pf_routing_tag_bypassroute "bypassRoute"     | Used to supersede normal routes as calculated by the network model between host/router; e.g., can be used to use a route that is not the shortest path for any of the shortest-path routing models. |
+| \ref pf_routing_tag_bypassasroute "bypassASroute"  | Used in the same way as bypassRoute, but for AS                                     |
 
 Basically all those tags will contain an (ordered) list of references
 to link that compose the route you want to define.
@@ -1152,27 +1264,26 @@ Consider the example below:
        <link_ctn id="link1"/>
        <link_ctn id="link2"/>
        <link_ctn id="link3"/>
-   </route>
+</route>
 \endverbatim
 
 The route here from host Alice to Bob will be first link1, then link2,
-and finally link3. What about the reverse route ? <b>route</b> and
-<b>ASroute</b> have an optional attribute <b>symmetrical</b>, that can
-be either YES or NO. YES means that the reverse route is the same
-route in the inverse order, and is set to YES by default. Note that
+and finally link3. What about the reverse route? \ref pf_routing_tag_route "Route" and
+\ref pf_routing_tag_asroute "ASroute" have an optional attribute \c symmetrical, that can
+be either \c YES or \c NO. \c YES means that the reverse route is the same
+route in the inverse order, and is set to \c YES by default. Note that
 this is not the case for bypass*Route, as it is more probable that you
 want to bypass only one default route.
 
-For an ASroute, things are just slightly more complicated, as you have
-to give the id of the gateway which is inside the AS you're talking
-about you want to access ... So it looks like this :
-
+For an \ref pf_routing_tag_asroute "ASroute", things are just slightly more complicated, as you have
+to give the id of the gateway which is inside the AS you want to access ... 
+So it looks like this:
 
 \verbatim
-  <ASroute src="AS1" dst="AS2"
-    gw_src="router1" gw_dst="router2">
-    <link_ctn id="link1"/>
-  </ASroute>
+<ASroute src="AS1" dst="AS2"
+  gw_src="router1" gw_dst="router2">
+  <link_ctn id="link1"/>
+</ASroute>
 \endverbatim
 
 gw == gateway, so when any message are trying to go from AS1 to AS2,
@@ -1180,37 +1291,41 @@ it means that it must pass through router1 to get out of the AS, then
 pass through link1, and get into AS2 by being received by router2.
 router1 must belong to AS1 and router2 must belong to AS2.
 
-\subsubsection pf_linkctn link_ctn
-
-a <b>link_ctn</b> is the tag that is used in order to reference a
-<b>link</b> in a route. Its id is the link id it refers to.
-
-<b>link_ctn</b> attributes :
-\li <b>id (mandatory)</b>: Id of the link this tag refers to
-\li <b>direction</b>: if the link referenced by <b>id</b> has been
-    declared as FULLDUPLEX, this is used to indicate in which
-    direction the route you're defining is going through this link.
-    Possible values "UP" or "DOWN".
-
-\subsubsection pf_asro ASroute
-
-ASroute tag purpose is to let people write manually their routes
-between AS. It's useful when you're in Full model.
-
-<b>ASroute</b> attributes :
-\li <b>src (mandatory)</b>: the source AS id.
-\li <b>dst (mandatory)</b>: the destination AS id.
-\li <b>gw_src (mandatory)</b>: the gateway to be used within the AS.
-    Can be any <b>host</b> or \b router defined into the \b src AS or
-    into one of the AS it includes.
-\li <b>gw_dst (mandatory)</b>: the gateway to be used within the AS.
-    Can be any <b>host</b> or \b router defined into the \b dst AS or
-    into one of the AS it includes.
-\li <b>symmetrical</b>: if the route is symmetric, the reverse route
-    will be the opposite of the one defined. Can be either YES or NO,
-    default is YES.
-
-<b>Example of ASroute with Full</b>
+\subsubsection pf_linkctn &lt;link_ctn/&gt;
+
+This entity has only one purpose: Refer to an already existing
+\ref pf_link "&lt;link/&gt;" when defining a route, i.e., it
+can only occur as a child of \ref pf_routing_tag_route "&lt;route/&gt;"
+
+| Attribute name  | Mandatory | Values | Description                                                   |
+| --------------- | --------- | ------ | -----------                                                   |
+| id              | yes       | String | The identifier of the link that should be added to the route. |
+| direction       | maybe     | UP\|DOWN | If the link referenced by \c id has been declared as \ref pf_sharing_policy_fullduplex "FULLDUPLEX", this indicates which direction the route traverses through this link: UP or DOWN. If you don't use FULLDUPLEX, this attribute has no effect.
+
+#### Example Files ####
+
+This is an automatically generated list of example files that use the \c &lt;link_ctn/gt;
+entity (the path is given relative to SimGrid's source directory):
+
+\verbinclude example_filelist_xmltag_linkctn
+
+\subsubsection pf_routing_tag_asroute ASroute
+
+The purpose of this entity is to define a route between two ASes.
+This is mainly useful when you're in the \ref pf_routing_model_full "Full routing model".
+
+#### Attributes ####
+
+| Attribute name  | Mandatory | Values | Description                                                                                                                                |
+| --------------- | --------- | ------ | -----------                                                                                                                                |
+| src             | yes       | String | The identifier of the source AS                                                                                                            |
+| dst             | yes       | String | See the \c src attribute                                                                                                                   |
+| gw_src          | yes       | String | The gateway that will be used within the src AS; this can be any \ref pf_host "Host" or \ref pf_router "Router" defined within the src AS. |
+| gw_dst          | yes       | String | Same as \c gw_src, but with the dst AS instead.                                                                                            |
+| symmetrical     | no        | YES\|NO (Default: YES) | If this route is symmetric, the opposite route (from dst to src) will also be declared implicitly.               | 
+
+#### Example ####
+
 \verbatim
 <AS  id="AS0"  routing="Full">
   <cluster id="my_cluster_1" prefix="c-" suffix=".me"
@@ -1236,78 +1351,86 @@ between AS. It's useful when you're in Full model.
 </AS>
 \endverbatim
 
-\subsubsection pf_ro route
-The principle is the same as ASroute : <b>route</b> contains list of
-links that are in the path between src and dst, except that it is for
-routes between a src that can be either <b>host</b> or \b router and a
-dst that can be either <b>host</b> or \b router. Useful for Full
-as well as for the shortest-paths based models, where you
-have to give topological information.
+\subsubsection pf_routing_tag_route route 
+
+The principle is the same as for 
+\ref pf_routing_tag_asroute "ASroute": The route contains a list of links that
+provide a path from \c src to \c dst. Here, \c src and \c dst can both be either a 
+\ref pf_host "host" or \ref pf_router "router".  This is mostly useful for the 
+\ref pf_routing_model_full "Full routing model" as well as for the 
+\ref pf_routing_model_shortest_path "shortest-paths" based models (as they require 
+topological information).
 
 
-<b>route</b> attributes :
-\li <b>src (mandatory)</b>: the source id.
-\li <b>dst (mandatory)</b>: the destination id.
-\li <b>symmetrical</b>: if the route is symmetric, the reverse route
-    will be the opposite of the one defined. Can be either YES or NO,
-    default is YES.
+| Attribute name  | Mandatory | Values                 | Description                                                                                        |
+| --------------- | --------- | ---------------------- | -----------                                                                                        |
+| src             | yes       | String                 | The value given to the source's "id" attribute                                                     |
+| dst             | yes       | String                 | The value given to the destination's "id" attribute.                                               |
+| symmetrical     | no        | YES\| NO (Default: YES) | If this route is symmetric, the opposite route (from dst to src) will also be declared implicitly. |
 
-<b>route example in Full</b>
+
+#### Examples ####
+
+A route in the \ref pf_routing_model_full "Full routing model" could look like this:
 \verbatim
  <route src="Tremblay" dst="Bourassa">
      <link_ctn id="4"/><link_ctn id="3"/><link_ctn id="2"/><link_ctn id="0"/><link_ctn id="1"/><link_ctn id="6"/><link_ctn id="7"/>
  </route>
+ </route>
 \endverbatim
 
-<b>route example in a shortest-path model</b>
+A route in the \ref pf_routing_model_shortest_path "Shortest-Path routing model" could look like this:
 \verbatim
- <route src="Tremblay" dst="Bourassa">
-     <link_ctn id="3"/>
-   </route>
+<route src="Tremblay" dst="Bourassa">
+  <link_ctn id="3"/>
+</route>
 \endverbatim
-Note that when using route to give topological information, you have
-to give routes with one link only in it, as SimGrid needs to know
-which host are at the end of the link.
+\note 
+    You must only have one link in your routes when you're using them to provide
+    topological information, as the routes here are simply the edges of the
+    (network-)graph and the employed algorithms need to know which edge connects
+    which pair of entities.
 
-\subsubsection pf_byASro bypassASroute
+\subsubsection pf_routing_tag_bypassasroute bypassASroute
 
-<b>Note : bypassASroute and bypassRoute are under rewriting to perform
-better ; so you may not use it yet</b> As said before, once you choose
-a model, it (if so) calculates routes for you. But maybe you want to
+%As said before, once you choose
+a model, it (most likely; the constant network model, for example, doesn't) calculates routes for you. But maybe you want to
 define some of your routes, which will be specific. You may also want
-to bypass some routes defined in lower level AS at an upper stage :
+to bypass some routes defined in lower level AS at an upper stage:
 <b>bypassASroute</b> is the tag you're looking for. It allows to
 bypass routes defined between already defined between AS (if you want
 to bypass route for a specific host, you should just use byPassRoute).
 The principle is the same as ASroute : <b>bypassASroute</b> contains
 list of links that are in the path between src and dst.
 
-<b>bypassASroute</b> attributes :
-\li <b>src (mandatory)</b>: the source AS id.
-\li <b>dst (mandatory)</b>: the destination AS id.
-\li <b>gw_src (mandatory)</b>: the gateway to be used within the AS.
-    Can be any <b>host</b> or \b router defined into the \b src AS or
-    into one of the AS it includes.
-\li <b>gw_dst (mandatory)</b>: the gateway to be used within the AS.
-    Can be any <b>host</b> or \b router defined into the \b dst AS or
-    into one of the AS it includes.
-\li <b>symmetrical</b>: if the route is symmetric, the reverse route
-    will be the opposite of the one defined. Can be either YES or NO,
-    default is YES.
-
-<b>bypassASroute Example</b>
+#### Attributes ####
+
+| Attribute name  | Mandatory | Values                  | Description                                                                                                  |
+| --------------- | --------- | ----------------------  | -----------                                                                                                  |
+| src             | yes       | String                  | The value given to the source AS's "id" attribute                                                            |
+| dst             | yes       | String                  | The value given to the destination AS's "id" attribute.                                                      |
+| gw_src          | yes       | String                  | The value given to the source gateway's "id" attribute; this can be any host or router within the src AS     |
+| gw_dst          | yes       | String                  | The value given to the destination gateway's "id" attribute; this can be any host or router within the dst AS|
+| symmetrical     | no        | YES\| NO (Default: YES) | If this route is symmetric, the opposite route (from dst to src) will also be declared implicitly. |
+
+#### Example ####
+
 \verbatim
-    <bypassASRoute src="my_cluster_1" dst="my_cluster_2"
-     gw_src="my_cluster_1_router"
-     gw_dst="my_cluster_2_router">
-        <link_ctn id="link_tmp"/>
-     </bypassASroute>
+<bypassASRoute src="my_cluster_1" dst="my_cluster_2"
+  gw_src="my_cluster_1_router"
+  gw_dst="my_cluster_2_router">
+    <link_ctn id="link_tmp"/>
+</bypassASroute>
 \endverbatim
 
-\subsubsection pf_byro bypassRoute
-<b>Note : bypassASRoute and bypassRoute are under rewriting to perform
-better ; so you may not use it yet</b> As said before, once you choose
-a model, it (if so) calculates routes for you. But maybe you want to
+This example shows that link \c link_tmp (definition not displayed here) directly
+connects the router \c my_cluster_1_router in the source cluster to the router
+\c my_cluster_2_router in the destination router. Additionally, as the \c symmetrical
+attribute was not given, this route is presumed to be symmetrical.
+
+\subsubsection pf_routing_tag_bypassroute bypassRoute
+
+%As said before, once you choose
+a model, it (most likely; the constant network model, for example, doesn't) calculates routes for you. But maybe you want to
 define some of your routes, which will be specific. You may also want
 to bypass some routes defined in lower level AS at an upper stage :
 <b>bypassRoute</b> is the tag you're looking for. It allows to bypass
@@ -1315,20 +1438,25 @@ routes defined between <b>host/router</b>. The principle is the same
 as route : <b>bypassRoute</b> contains list of links references of
 links that are in the path between src and dst.
 
-<b>bypassRoute</b> attributes :
-\li <b>src (mandatory)</b>: the source AS id.
-\li <b>dst (mandatory)</b>: the destination AS id.
-\li <b>symmetrical</b>: if the route is symmetric, the reverse route
-    will be the opposite of the one defined. Can be either YES or NO,
-    default is YES.
+#### Attributes ####
+
+| Attribute name  | Mandatory | Values                  | Description                                                                                                  |
+| --------------- | --------- | ----------------------  | -----------                                                                                                  |
+| src             | yes       | String                  | The value given to the source AS's "id" attribute                                                            |
+| dst             | yes       | String                  | The value given to the destination AS's "id" attribute.                                                      |
+| symmetrical     | no        | YES \| NO (Default: YES) | If this route is symmetric, the opposite route (from dst to src) will also be declared implicitly. |
+
+#### Examples ####
 
-<b>bypassRoute Example</b>
 \verbatim
-    <bypassRoute src="host_1" dst="host_2">
-        <link_ctn id="link_tmp"/>
-     </bypassRoute>
+<bypassRoute src="host_1" dst="host_2">
+   <link_ctn id="link_tmp"/>
+</bypassRoute>
 \endverbatim
 
+This example shows that link \c link_tmp (definition not displayed here) directly
+connects host \c host_1 to host \c host_2. Additionally, as the \c symmetrical
+attribute was not given, this route is presumed to be symmetrical.
 
 \subsection pb_baroex Basic Routing Example
 
@@ -1337,7 +1465,7 @@ and AS_2. If you want to make a host (h1) from AS_1 with another one
 (h2) from AS_2 then you'll have to proceed as follows:
 \li First, you have to ensure that a route is defined from h1 to the
     AS_1's exit gateway and from h2 to AS_2's exit gateway.
-\li Then, you'll have to define a route between AS_1 to AS_2. As those
+\li Then, you'll have to define a route between AS_1 to AS_2. %As those
     AS are both resources belonging to AS_Big, then it has to be done
     at AS_big level. To define such a route, you have to give the
     source AS (AS_1), the destination AS (AS_2), and their respective
@@ -1347,18 +1475,18 @@ and AS_2. If you want to make a host (h1) from AS_1 with another one
     defined inside AS_Big. If you choose some shortest-path model,
     this route will be computed automatically.
 
-As said before, there are mainly 2 tags for routing :
+%As said before, there are mainly 2 tags for routing :
 \li <b>ASroute</b>: to define routes between two  <b>AS</b>
 \li <b>route</b>: to define routes between two <b>host/router</b>
 
-As we are dealing with routes between AS, it means that those we'll
+%As we are dealing with routes between AS, it means that those we'll
 have some definition at AS_Big level. Let consider AS_1 contains 1
 host, 1 link and one router and AS_2 3 hosts, 4 links and one router.
 There will be a central router, and a cross-like topology. At the end
 of the crosses arms, you'll find the 3 hosts and the router that will
 act as a gateway. We have to define routes inside those two AS. Let
 say that AS_1 contains full routes, and AS_2 contains some Floyd
-routing (as we don't want to bother with defining all routes). As
+routing (as we don't want to bother with defining all routes). %As
 we're using some shortest path algorithms to route into AS_2, we'll
 then have to define some <b>route</b> to gives some topological
 information to SimGrid. Here is a file doing it all :
@@ -1403,27 +1531,32 @@ information to SimGrid. Here is a file doing it all :
 
 There are 3 tags, that you can use inside a \<platform\> tag that are
 not describing the platform:
-\li random: it allows you to define random generators you want to use
+\li \ref pf_random "random": it allows you to define random generators you want to use
     for your simulation.
-\li config: it allows you to pass some configuration stuff like, for
+\li \ref pf_config "config": it allows you to pass some configuration stuff like, for
     example, the network model and so on. It follows the
-\li include: simply allows you to include another file into the
-    current one.
+\li \ref pf_include "include": allows you to include another file into the current one.
 
-\subsection pf_conf config
-<b>config</b> attributes :
-\li <b>id (mandatory)</b>: the identifier of the config to be used
-    when referring to it.
+\subsection pf_config config
 
+The only purpose of this tag is to contain the \c prop tags, as described below.
+These tags will then configure the options as described by Section \ref options.
+(See the example)
 
-<b>config</b> tag only purpose is to include <b>prop</b> tags. Valid
-id are basically the same as the list of possible parameters you can
-use by command line, except that "/" are used for namespace
-definition. See the \ref options config and options page for more
-information.
+#### Attributes ####
+
+| Attribute name  | Mandatory | Values                  | Description                                                                                                  |
+| --------------- | --------- | ----------------------  | -----------                                                                                                  |
+| id              | yes       | String                  | The identifier of the config tag when referring to id; this is basically useless, though.                    |
 
+#### Possible children ####
+
+Tag name        | Description | Documentation
+------------    | ----------- | -------------
+\<prop/\>       | The prop tag allows you to define different configuration options following the attribute/value schema. See the \ref options page. | N/A
+
+#### Example ####
 
-<b>config example</b>
 \verbatim
 <?xml version='1.0'?>
 <!DOCTYPE platform SYSTEM "http://simgrid.gforge.inria.fr/simgrid.dtd">
@@ -1442,24 +1575,35 @@ information.
 \endverbatim
 
 
-\subsection pf_rand random
-Not yet in use, and possibly subject to huge modifications.
+\subsection pf_random random
+
+<b>This has not yet been implemented.</b>
+
+\subsection pf_include include
 
-\subsection pf_incl include
-<b>include</b> tag allows to import into a file platform parts located
-in another file. This is done with the intention to help people
+The \c include tag allows you to import other platforms into your
+local file. This is done with the intention to help people
 combine their different AS and provide new platforms. Those files
-should contains XML part that contains either
-<b>include,cluster,peer,AS,trace,trace_connect</b> tags.
+should contain XML that consists of 
+\ref pf_include "include", \ref pf_cluster "cluster", \ref pf_peer "peer", \ref pf_As "AS", \ref pf_trace "trace", \ref pf_trace "tags".
 
-<b>include</b> attributes :
-\li <b>file (mandatory)</b>: filename of the file to include. Possible
-    values: absolute or relative path, syntax similar to the one in
-    use on your system.
+\note
+    Due to some obscure technical reasons, you have to open
+    and close the tag in order to make it work.
+
+#### Attributes ####
+
+| Attribute name  | Mandatory | Values                  | Description                                                                                                  |
+| --------------- | --------- | ----------------------  | -----------                                                                                                  |
+| file            | yes       | String                  | Filename of the path you want to include with either relative or absolute path. Syntax is defined by your OS |
+
+
+#### Example ####
+
+The following example includes two files, clusterA.xml and clusterB.xml and
+combines them two one platform file; all hosts, routers etc. defined in 
+each of them will then be usable.
 
-<b>Note</b>: due to some obscure technical reasons, you have to open
-and close tag in order to let it work.
-<b>include Example</b>
 \verbatim
 <?xml version='1.0'?>
 <!DOCTYPE platform SYSTEM "http://simgrid.gforge.inria.fr/simgrid.dtd">
@@ -1471,35 +1615,42 @@ and close tag in order to let it work.
 </platform>
 \endverbatim
 
-\subsection pf_tra trace and trace_connect
-Both tags are an alternate way to passe availability, state, and so on
-files to entity. Instead of referring to the file directly in the host,
-link, or cluster tag, you proceed by defining a trace with an id
-corresponding to a file, later a host/link/cluster, and finally using
-trace_connect you say that the file trace must be used by the entity.
-Get it ? Let's have a look at an example :
+\subsection pf_trace trace and trace_connect
+
+Both tags are an alternate way to pass files containing information on
+availability, state etc. to an entity. (See also, for instance, Section \ref
+pf_host_churn "Churn", as described for the host entity.) Instead of referring
+to the file directly in the host, link, or cluster tag, you proceed by defining
+a trace with an id corresponding to a file, later a host/link/cluster, and
+finally using trace_connect you say that the file trace must be used by the
+entity. 
+
+
+#### Example #### 
 
 \verbatim
 <AS  id="AS0"  routing="Full">
   <host id="bob" power="1000000000"/>
 </AS>
-  <trace id="myTrace" file="bob.trace" periodicity="1.0"/>
-  <trace_connect trace="myTrace" element="bob" kind="POWER"/>
+<trace id="myTrace" file="bob.trace" periodicity="1.0"/>
+<trace_connect trace="myTrace" element="bob" kind="POWER"/>
 \endverbatim
 
-All constraints you have is that <b>trace_connect</b> is after
-<b>trace</b> and <b>host</b> definitions.
+\note 
+    The order here is important.  \c trace_connect must come 
+    after the elements \c trace and \c host, as both the host
+    and the trace definition must be known when \c trace_connect
+    is parsed; the order of \c trace and \c host is arbitrary.
 
 
-<b>trace</b> attributes :
-\li <b>id (mandatory)</b>: the identifier of the trace to be used when
-    referring to it.
-\li <b>file</b>: filename of the file to include. Possible values :
-    absolute or relative path, syntax similar to the one in use on
-    your system. If omitted, the system expects that you provide the
-    trace values inside the trace tags (see below).
-\li <b>trace periodicity (mandatory)</b>: trace periodicity, same
-    definition as in hosts (see upper for details).
+#### \c trace attributes ####
+
+
+| Attribute name  | Mandatory | Values                 | Description                                                                                       |
+| --------------- | --------- | ---------------------- | -----------                                                                                       |
+| id              | yes       | String                 | Identifier of this trace; this is the name you pass on to \c trace_connect.                       |
+| file            | no        | String                 | Filename of the file that contains the information - the path must follow the style of your OS. You can omit this, but then you must specifiy the values inside of &lt;trace&gt; and &lt;/trace&gt; - see the example below. |
+| trace_periodicity | yes | String | This is the same as for \ref pf_host "hosts" (see there for details) |
 
 Here is an example  of trace when no file name is provided:
 
@@ -1508,17 +1659,16 @@ Here is an example  of trace when no file name is provided:
     0.0 1.0
     11.0 0.5
     20.0 0.8
 </trace>
+ </trace>
 \endverbatim
 
-<b>trace_connect</b> attributes :
-\li <b>kind</b>: the type of trace, possible values
-    <b>HOST_AVAIL|POWER|LINK_AVAIL|BANDWIDTH|LATENCY,</b>  default:
-    <b>HOST_AVAIL</b>
-\li <b>trace (mandatory)</b>: the identifier of the trace referenced.
-\li <b>element (mandatory)</b>: the identifier of the entity referenced.
-
+#### \c trace_connect attributes ####
 
+| Attribute name  | Mandatory | Values                 | Description                                                                                       |
+| --------------- | --------- | ---------------------- | -----------                                                                                       |
+| kind            | no        | HOST_AVAIL\|POWER\|<br/>LINK_AVAIL\|BANDWIDTH\|LATENCY (Default: HOST_AVAIL)   | Describes the kind of trace.                   |
+| trace           | yes       | String                 | Identifier of the referenced trace (specified of the trace's \c id attribute)                     |
+| element         | yes       | String                 | The identifier of the referenced entity as given by its \c id attribute                           |
 
 \section pf_hints Hints and tips, or how to write a platform efficiently
 
@@ -1644,7 +1794,7 @@ This is currently a convention and we may offer to change this convention in the
 You may have noted that conveniently, a peer named FOO defines an AS named FOO and a router named router_FOO, which is why it works seamlessly with the <b>peer</b> tag.
 
 
-\subsection pf_wisely Choosing wisely the routing model to use
+\subsection pf_routing_howto_choose_wisely Choosing wisely the routing model to use
 
 
 Choosing wisely the routing model to use can significantly fasten your
index ab415b2..76b528a 100644 (file)
@@ -1,9 +1,13 @@
 /*! \page pls Packet level simulation
 
+\tableofcontents
+
 It is possible to use a packet-level network simulator
 instead of the default flow-based simulation. You may want to use such
 an approach if you have doubts about the validity of the default model
-or if you want to perform some validation experiments. 
+or if you want to perform some validation experiments. At the moment,
+we support the NS3 simulator; see Section \ref pls_examples "Examples" for 
+some additional information.
 
 At the moment, we only support the NS3 simulator. Previous versions of
 SimGrid did support the GTNetS simulator and that support could
@@ -102,4 +106,9 @@ file that you will provide. There is some caveats to know:
 
 More about ns-3 simulator <a href="http://www.nsnam.org/">(Official website)</a>
 
+\subsection pls_examples Examples
+
+There are some examples in the \c examples/ folder, that show how to use
+the bindings; see also the \ref MSG_ex_PLS "documentation for these examples".
+
 */
index 20276a8..c520067 100644 (file)
@@ -1110,15 +1110,15 @@ div.toc li.level1 {
 }
 
 div.toc li.level2 {
-        margin-left: 15px;
+        /*margin-left: 15px;*/
 }
 
 div.toc li.level3 {
-        margin-left: 30px;
+        /*margin-left: 30px;*/
 }
 
 div.toc li.level4 {
-        margin-left: 45px;
+        /*margin-left: 45px;*/
 }
 
 .inherit_header {
index 2c4a4d8..b4b203e 100644 (file)
@@ -452,7 +452,7 @@ the beggining and size of the time slice.
 
 \subsubsection tracing_viva_graph Hierarchical Graph View
 
-As stated above (see section \ref tracing_tracing_analyzing), one
+%As stated above (see section \ref tracing_tracing_analyzing), one
 possibility to analyze SimGrid traces is to use Viva's graph view with
 a graph configuration to customize the graph according to the
 traces. A valid graph configuration (we are using the non-XML <a
index 665cba9..3526b42 100644 (file)
@@ -33,7 +33,7 @@ int master(int argc, char *argv[])
 
   int i;
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%d", &number_of_tasks);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%d", &number_of_tasks);
   xbt_assert(res,"Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &task_comp_size);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
@@ -95,7 +95,7 @@ int master(int argc, char *argv[])
 int worker(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   while (1) {
     res = MSG_task_receive(&(task),MSG_host_get_name(MSG_host_self()));
     xbt_assert(res == MSG_OK, "MSG_task_receive failed");
index f4da400..2d44af8 100644 (file)
@@ -44,7 +44,7 @@ int master(int argc, char *argv[])
 
   int i;
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%d", &number_of_tasks);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%d", &number_of_tasks);
   xbt_assert(res,"Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &task_comp_size);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
@@ -110,7 +110,7 @@ int master(int argc, char *argv[])
 int worker(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   char channel[1024];
 
   build_channel_name(channel,MSG_process_get_data(MSG_process_self()),
index b8cdc8d..4ac7469 100644 (file)
@@ -44,7 +44,7 @@ int master(int argc, char *argv[])
 
   int i;
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%lg", &timeout);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%lg", &timeout);
   xbt_assert(res,"Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &task_comp_size);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
@@ -107,7 +107,7 @@ int master(int argc, char *argv[])
 int worker(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   char channel[1024];
 
   build_channel_name(channel,MSG_process_get_data(MSG_process_self()),
index 85f16da..75f351d 100644 (file)
@@ -46,7 +46,7 @@ int master(int argc, char *argv[])
 
   TRACE_category(master_name);
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%lg", &timeout);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%lg", &timeout);
   xbt_assert(res,"Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &task_comp_size);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
@@ -110,7 +110,7 @@ int master(int argc, char *argv[])
 int worker(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   char channel[1024];
 
   build_channel_name(channel,MSG_process_get_data(MSG_process_self()),
index 68ae6ee..c50a067 100644 (file)
@@ -46,7 +46,7 @@ int master(int argc, char *argv[])
 
   TRACE_category(master_name);
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%lg", &timeout);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%lg", &timeout);
   xbt_assert(res,"Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &task_comp_size);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
@@ -136,7 +136,7 @@ int master(int argc, char *argv[])
 int worker(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   char channel[1024];
 
   const char *my_master = MSG_process_get_data(MSG_process_self());
diff --git a/doc/webcruft/storage_sample_scenario.png b/doc/webcruft/storage_sample_scenario.png
new file mode 100644 (file)
index 0000000..3315d41
Binary files /dev/null and b/doc/webcruft/storage_sample_scenario.png differ
index b3676d2..e2c117f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(tesh_files
   ${tesh_files}
   PARENT_SCOPE
index b150f79..e9eaec2 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_async)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/AsyncTest.java
index ef9e1ab..0b5b2f0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_bittorrent)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Bittorrent.java
index d4ea09e..155957f 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2013-2014. The SimGrid Team.
 # All rights reserved.
index 48b0439..7d405b9 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_chord)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Chord.java
index 555cc84..9a0b708 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_cloud)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Cloud.java
index 4967240..113327a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_cloud_migration)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Daemon.java
index 7ff9534..b148630 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_commTime)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/CommTimeTest.java
index f954ee3..07f5b09 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_io)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/IO.java
index e7807e8..9fdbd0d 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_kademlia)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Answer.java
index a1cdd0c..f50080a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_master_slave_bypass)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/FinalizeTask.java
index 304876c..5934665 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_master_slave_kill)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/FinalizeTask.java
index 8f83bfc..e63b2ef 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_masterslave)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/FinalizeTask.java
index 7bd6bb9..77ee4e0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_migration)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Emigrant.java
index ef79d5c..3ec0b1f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_mutualExclusion)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Coordinator.java
index 07e750a..5bc1856 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_pingPong)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/PingPongTask.java
index 202d0e5..c1f9d0e 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_priority)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Priority.java
index a136bcc..b712ab0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_reservation_surf_plugin)
 set(sources
    ${CMAKE_CURRENT_SOURCE_DIR}/TestPlugin.java
index 4030159..b373904 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_startKillTime)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Master.java
index 1f41104..4353388 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_surf_cpu_model)
 set(sources
    ${CMAKE_CURRENT_SOURCE_DIR}/TestCpuModel.java
index 81bde88..85a399a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_surf_plugin)
 set(sources
    ${CMAKE_CURRENT_SOURCE_DIR}/TestPlugin.java
index 42cec94..80ac4e0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_suspend)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/DreamMaster.java
index ecc7337..55720c7 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_tracing)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/PingPongTask.java
index 90ecd20..410adaf 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(tesh_files
   ${tesh_files}
   ${CMAKE_CURRENT_SOURCE_DIR}/bittorrent/bittorrent.tesh
index fc23726..cd08b29 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(tesh_files
   ${tesh_files}
   PARENT_SCOPE
index 2a7add2..a4a8332 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 add_executable(actions actions.c)
 add_executable(storage_actions storage_actions.c)
index cada54a..f4c0b9c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(bittorrent
index f3460bb..7f0d6d4 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2012, 2014. The SimGrid Team.
 # All rights reserved.
index 892f0fe..f84ab26 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(chainsend chainsend.c iterator.c common.c messages.c broadcaster.c peer.c)
index 32f0192..5a01af2 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(chord chord.c)
index afc0ea9..3b707ac 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2011-2012, 2014. The SimGrid Team.
 # All rights reserved.
index aba884a..f35515c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(master_worker_vm "master_worker_vm.c")
index c3273d8..a713137 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(energy_consumption energy_consumption.c)
index 3dc2228..7f942d6 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(onoff onoff.c)
index c5f1695..5446266 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(pstate pstate.c)
index 53ba578..1155dd9 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(exception exception.c)
index 9017ddc..a2ebe2b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(test_MSG_gpu_task_create "test_MSG_gpu_task_create.c")
index cdf94db..1a1866b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(gtnets gtnets.c)
index 38b44f4..c1b2728 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(peer peer.c)
index f35d0af..1251630 100644 (file)
@@ -97,7 +97,7 @@ int sender(int argc, char *argv[])
 int receiver(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED msg_error_t res;
+  XBT_ATTRIB_UNUSED msg_error_t res;
   int id = -1;
   char mailbox[80];
   msg_comm_t res_irecv;
@@ -106,7 +106,7 @@ int receiver(int argc, char *argv[])
   XBT_INFO("sleep_start_time : %f , sleep_test_time : %f", sleep_start_time,
         sleep_test_time);
 
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
   read = sscanf(argv[1], "%d", &id);
   xbt_assert(read,
               "Invalid argument %s\n", argv[1]);
index 758fae5..22c4aff 100644 (file)
@@ -69,11 +69,11 @@ int sender(int argc, char *argv[])
 int receiver(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED msg_error_t res;
+  XBT_ATTRIB_UNUSED msg_error_t res;
   int id = -1;
   char mailbox[80];
   msg_comm_t res_irecv;
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
   read = sscanf(argv[1], "%d", &id);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
   MSG_process_sleep(10);
index c3fea50..154fa9d 100644 (file)
@@ -69,7 +69,7 @@ int sender(int argc, char *argv[])
   sprintf(mailbox, "finalize");
 
   msg_comm_t res_irecv;
-  _XBT_GNUC_UNUSED msg_error_t res_wait;
+  XBT_ATTRIB_UNUSED msg_error_t res_wait;
   for (i = 0; i < receivers_count; i++) {
     task = NULL;
     res_irecv = MSG_task_irecv(&(task), mailbox);
@@ -93,7 +93,7 @@ int receiver(int argc, char *argv[])
   int tasks = atof(argv[2]);
   msg_task_t *task = xbt_new(msg_task_t, tasks);
 
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
   read = sscanf(argv[1], "%d", &id);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
   sprintf(mailbox, "receiver-%d", id);
@@ -109,7 +109,7 @@ int receiver(int argc, char *argv[])
   /* Here we are waiting for the receiving of all communications */
   msg_task_t task_com;
   while (!xbt_dynar_is_empty(comms)) {
-    _XBT_GNUC_UNUSED msg_error_t err;
+    XBT_ATTRIB_UNUSED msg_error_t err;
     xbt_dynar_remove_at(comms, MSG_comm_waitany(comms), &res_irecv);
     task_com = MSG_comm_get_task(res_irecv);
     MSG_comm_destroy(res_irecv);
index b8c0a04..ec3dd37 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(file file.c)
index 01b3c6a..cfe5ef3 100644 (file)
@@ -12,6 +12,7 @@ $ ${bindir:=.}/io/file ${srcdir:=.}/examples/platforms/storage/storage.xml "--lo
 >              Storage Id: 'Disk4'
 >              Storage Type: 'single_SSD'
 >              Content Type: 'txt_unix'
+>              File Descriptor Id: 0
 > [  0.000000] (1:0@denise)    Open file '/home/doc/simgrid/examples/platforms/g5k.xml'
 > [  0.000000] (2:1@alice)     Capacity of the storage element 'c:\Windows\setupact.log' is stored on: 2391537133 / 536870912000
 > [  0.000000] (3:2@carl)      Capacity of the storage element '/home/doc/simgrid/examples/platforms/g5k_cabinets.xml' is stored on: 36946053 / 536870912000
index e3ca838..f07cafd 100644 (file)
@@ -14,6 +14,7 @@ $ ${bindir:=.}/io/remote$EXEEXT ${srcdir:=.}/examples/platforms/storage/remote_i
 >              Storage Id: 'Disk2'
 >              Storage Type: 'SATA-II_HDD'
 >              Content Type: 'txt_windows'
+>              File Descriptor Id: 0
 > [  0.000000] (2@  bob) File Descriptor information:
 >              Full path: '/scratch/lib/libsimgrid.so.3.6.2'
 >              Size: 12710497
@@ -21,6 +22,7 @@ $ ${bindir:=.}/io/remote$EXEEXT ${srcdir:=.}/examples/platforms/storage/remote_i
 >              Storage Id: 'Disk1'
 >              Storage Type: 'SATA-II_HDD'
 >              Content Type: 'txt_unix'
+>              File Descriptor Id: 0
 > [  0.000000] (3@ carl) File Descriptor information:
 >              Full path: '/scratch/lib/libsimgrid.so.3.6.2'
 >              Size: 12710497
@@ -28,6 +30,7 @@ $ ${bindir:=.}/io/remote$EXEEXT ${srcdir:=.}/examples/platforms/storage/remote_i
 >              Storage Id: 'Disk1'
 >              Storage Type: 'SATA-II_HDD'
 >              Content Type: 'txt_unix'
+>              File Descriptor Id: 0
 > [  0.000000] (4@ dave) File Descriptor information:
 >              Full path: 'c:\Windows\bootstat.dat'
 >              Size: 67584
@@ -35,6 +38,7 @@ $ ${bindir:=.}/io/remote$EXEEXT ${srcdir:=.}/examples/platforms/storage/remote_i
 >              Storage Id: 'Disk2'
 >              Storage Type: 'SATA-II_HDD'
 >              Content Type: 'txt_windows'
+>              File Descriptor Id: 0
 > [  0.000000] (1@alice) Try to read 101663 from 'c:\Windows\setupact.log'
 > [  0.000000] (2@  bob) Try to read 12710497 from '/scratch/lib/libsimgrid.so.3.6.2'
 > [  0.000000] (3@ carl) Try to read 12710497 from '/scratch/lib/libsimgrid.so.3.6.2'
index 00412a4..662489e 100644 (file)
@@ -18,6 +18,7 @@ $ ${bindir:=.}/io/storage$EXEEXT ${srcdir:=.}/examples/platforms/storage/storage
 >              Storage Id: 'Disk4'
 >              Storage Type: 'single_SSD'
 >              Content Type: 'txt_unix'
+>              File Descriptor Id: 0
 > [  0.003333] (1:(null)@denise) Free size: 536857490006 bytes
 > [  0.003333] (1:(null)@denise) Used size: 13421994 bytes
 > [  0.004333] (1:(null)@denise) Read 200000 bytes on /home/tmp/data.txt
@@ -29,6 +30,7 @@ $ ${bindir:=.}/io/storage$EXEEXT ${srcdir:=.}/examples/platforms/storage/storage
 >              Storage Id: 'Disk4'
 >              Storage Type: 'single_SSD'
 >              Content Type: 'txt_unix'
+>              File Descriptor Id: 0
 > [  0.006000] (1:(null)@denise) *** Move '/tmp/data.txt' into '/tmp/simgrid.readme'
 > [  0.006000] (1:(null)@denise) User data attached to the file: 777
 > [  0.006000] (1:(null)@denise) *** Get/set data for storage element: Disk4 ***
index ced0003..19b6f1a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(kademlia "kademlia.c" "node.c" "routing_table.c"
index b475120..1b9526c 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2012, 2014. The SimGrid Team.
 # All rights reserved.
index 026a2de..310ddbc 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(masterslave_failure "masterslave_failure.c")
index 19b76d5..27f1602 100644 (file)
@@ -67,7 +67,7 @@ int master(int argc, char *argv[])
 int slave(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
 
   XBT_DEBUG("mailbox: %s",MSG_process_get_name(MSG_process_self()));
   while (1) {
index bb54684..1ff3e3a 100644 (file)
@@ -165,7 +165,7 @@ int master(int argc, char *argv[])
   double task_comp_size = 0;
   double task_comm_size = 0;
   int i;
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
 
   read = sscanf(argv[1], "%d", &number_of_tasks);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
index 6d1bba8..e6bc021 100644 (file)
@@ -32,7 +32,7 @@ int master(int argc, char *argv[])
   double task_comp_size = 0;
   double task_comm_size = 0;
   int i;
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
 
   read = sscanf(argv[1], "%d", &number_of_tasks);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
index 0e9d2fb..ce4eec9 100644 (file)
@@ -30,7 +30,7 @@ int master(int argc, char *argv[])
   double task_comp_size = 0;
   double task_comm_size = 0;
   int i;
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
 
   read = sscanf(argv[1], "%d", &number_of_tasks);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
index 7b2c01e..01e1eb7 100644 (file)
@@ -43,7 +43,7 @@ int master(int argc, char *argv[])
 
   int i;
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%d", &number_of_tasks);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%d", &number_of_tasks);
   xbt_assert(res,"Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &task_comp_size);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
@@ -107,7 +107,7 @@ int master(int argc, char *argv[])
 int slave(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   while (1) {
     res = MSG_task_receive(&(task),MSG_host_get_name(MSG_host_self()));
     xbt_assert(res == MSG_OK, "MSG_task_get failed");
index 16d2efc..7a5ddbb 100644 (file)
@@ -65,10 +65,10 @@ int master(int argc, char *argv[])
 int slave(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   int id = -1;
   char mailbox[80];
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
 
   read = sscanf(argv[1], "%d", &id);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
index fb51f84..447e5a7 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(HAVE_MC)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
index 8e13b82..3fe3998 100644 (file)
@@ -2,7 +2,7 @@
 
 ! expect return 1
 ! timeout 20
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1 --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --log=xbt_cfg.thresh:warning --cfg=contexts/stack_size:256
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --log=xbt_cfg.thresh:warning --cfg=contexts/stack_size:256
 > [  0.000000] (0:@) Check a safety property
 > [  0.000000] (2:client@HostB) Sent!
 > [  0.000000] (3:client@HostC) Sent!
index 9f0b7ad..0b0d494 100644 (file)
@@ -2,7 +2,7 @@
 
 ! expect return 2
 ! timeout 20
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness.xml --log=xbt_cfg.thresh:warning --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=contexts/stack_size:256 --cfg=model-check/property:promela_bugged1_liveness
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness.xml --log=xbt_cfg.thresh:warning "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=contexts/stack_size:256 --cfg=model-check/property:promela_bugged1_liveness
 > [  0.000000] (0:@) Check the liveness property promela_bugged1_liveness
 > [  0.000000] (2:client@Boivin) Ask the request
 > [  0.000000] (3:client@Fafard) Ask the request
index bc96e3b..927463a 100644 (file)
@@ -2,7 +2,7 @@
 
 ! expect return 2
 ! timeout 60
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness.xml --log=xbt_cfg.thresh:warning --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=contexts/stack_size:256 --cfg=model-check/sparse-checkpoint:yes --cfg=model-check/property:promela_bugged1_liveness
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness.xml --log=xbt_cfg.thresh:warning "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=contexts/stack_size:256 --cfg=model-check/sparse-checkpoint:yes --cfg=model-check/property:promela_bugged1_liveness
 > [  0.000000] (0:@) Check the liveness property promela_bugged1_liveness
 > [  0.000000] (2:client@Boivin) Ask the request
 > [  0.000000] (3:client@Fafard) Ask the request
index 2f372b6..a1619a4 100755 (executable)
@@ -32,7 +32,7 @@ run() {
   timeout 30s ${bindir:=.}/bugged1_liveness_cleaner_$state \
     ${srcdir:=.}/../../platforms/platform.xml \
     ${srcdir:=.}/deploy_bugged1_liveness.xml \
-    --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" \
+    "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" \
     --cfg=contexts/factory:ucontext \
     --cfg=contexts/stack_size:256
   assert 'test $? = 134'
index fd040b4..54470cb 100644 (file)
@@ -2,7 +2,7 @@
 
 ! expect return 2
 ! timeout 90
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness_visited.xml --log=xbt_cfg.thresh:warning --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=model-check/visited:100 --cfg=contexts/stack_size:256  --cfg=model-check/property:promela_bugged1_liveness
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness_visited.xml --log=xbt_cfg.thresh:warning "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=model-check/visited:100 --cfg=contexts/stack_size:256  --cfg=model-check/property:promela_bugged1_liveness
 > [  0.000000] (0:@) Check the liveness property promela_bugged1_liveness
 > [  0.000000] (2:client@Boivin) Ask the request
 > [  0.000000] (3:client@Fafard) Ask the request
index 9fe46b0..64f7cbe 100644 (file)
@@ -2,7 +2,7 @@
 
 ! expect return 2
 ! timeout 90
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness_visited.xml --log=xbt_cfg.thresh:warning --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=model-check/visited:100 --cfg=contexts/stack_size:256 --cfg=model-check/sparse-checkpoint:yes  --cfg=model-check/property:promela_bugged1_liveness
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged1_liveness ${srcdir:=.}/../../platforms/platform.xml ${srcdir:=.}/deploy_bugged1_liveness_visited.xml --log=xbt_cfg.thresh:warning "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --cfg=contexts/factory:ucontext --cfg=model-check/visited:100 --cfg=contexts/stack_size:256 --cfg=model-check/sparse-checkpoint:yes  --cfg=model-check/property:promela_bugged1_liveness
 > [  0.000000] (0:@) Check the liveness property promela_bugged1_liveness
 > [  0.000000] (2:client@Boivin) Ask the request
 > [  0.000000] (3:client@Fafard) Ask the request
index 4449cbe..b25adad 100644 (file)
@@ -2,7 +2,7 @@
 
 ! expect return 1
 ! timeout 20
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged2 --cfg=model-check:1 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --log=xbt_cfg.thresh:warning --cfg=contexts/stack_size:256
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/bugged2 "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --log=xbt_cfg.thresh:warning --cfg=contexts/stack_size:256
 > [  0.000000] (0:@) Check a safety property
 > [  0.000000] (2:client@HostB) Send 1!
 > [  0.000000] (3:client@HostC) Send 2!
index f5b08c3..1e14eb3 100644 (file)
@@ -1,6 +1,6 @@
 #! ./tesh
 
-$ ${bindir:=.}/centralized --cfg=model-check:1
+$ ${bindir:=.}/centralized
 > [Fafard:client:(2) 0.000000] [centralized/INFO] Ask the request
 > [Boivin:client:(3) 0.000000] [centralized/INFO] Ask the request
 > [TeX:client:(4) 0.000000] [centralized/INFO] Ask the request
index cd13832..7c03627 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(migration migration.c)
index 56541cc..32ae25e 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(HAVE_NS3)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
index 9512a4c..5d7e81a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(parallel_task parallel_task.c)
index 382555e..1618944 100644 (file)
@@ -43,7 +43,7 @@ int execute(int argc, char *argv[])
                 "Unknown host %s. Stopping Now! ", argv[i]);
   }
 
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
   read = sscanf(argv[argc - 2], "%lg", &computation_amount);
   xbt_assert(read, "Invalid argument %s\n", argv[argc - 2]);
   read = sscanf(argv[argc - 1], "%lg", &communication_amount);
@@ -99,7 +99,7 @@ int redistribute(int argc, char *argv[])
                 "Unknown host %s. Stopping Now! ", argv[i]);
   }
 
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
   read = sscanf(argv[argc - 1], "%lg", &communication_amount);
   xbt_assert(read, "Invalid argument %s\n", argv[argc - 1]);
   computation_duration = (double *) calloc(host_list_size, sizeof(double));
index 39aef6b..bb90ae5 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(pastry pastry.c)
index 2e48d86..c08ea02 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(msg_pmm     msg_pmm.c)
index 700796e..38ccc18 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(priority priority.c)
index bd7ad2b..f1efaa6 100644 (file)
@@ -28,7 +28,7 @@ static int test(int argc, char *argv[])
   double priority = 1.0;
   msg_task_t task = NULL;
 
-  _XBT_GNUC_UNUSED int res = sscanf(argv[1], "%lg", &computation_amount);
+  XBT_ATTRIB_UNUSED int res = sscanf(argv[1], "%lg", &computation_amount);
   xbt_assert(res, "Invalid argument %s\n", argv[1]);
   res = sscanf(argv[2], "%lg", &priority);
   xbt_assert(res, "Invalid argument %s\n", argv[2]);
index ac68ede..07770b1 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(msg_prop msg_prop.c)
index 37a2dd4..c77494e 100644 (file)
@@ -99,7 +99,7 @@ int bob(int argc, char *argv[])
   xbt_dict_cursor_t cursor = NULL;
   char *key, *data;
   const char *noexist = "UnknownProcessProp";
-  _XBT_GNUC_UNUSED const char *value;
+  XBT_ATTRIB_UNUSED const char *value;
 
   XBT_INFO("== Print the properties of the process");
   xbt_dict_foreach(props, cursor, key, data)
index d8b48dd..6cbdbb3 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(synchro synchro.c)
index 837ca72..fbfa614 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(sendrecv sendrecv.c)
index e7e84a8..6b95310 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(sk_time "sk_time.c")
index cb358b8..1e6388f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(suspend suspend.c)
index c6d5f01..12a15d1 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(token_ring ring_call.c)
index dbe653d..5b7a39d 100644 (file)
@@ -33,7 +33,7 @@ int host(int argc, char *argv[])
   int host_number = atoi(MSG_process_get_name(MSG_process_self()));
   char mailbox[256];
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   if (host_number == 0){ //master  send then receive
     sprintf(mailbox, "%d", host_number+1);
     task = MSG_task_create("Token", task_comp_size, task_comm_size, NULL);
index c36d023..99002a2 100644 (file)
@@ -30,7 +30,7 @@ int host(int argc, char *argv[])
   int host_number = atoi(MSG_process_get_name(MSG_process_self()));
   char mailbox[256];
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   if (host_number == 0){ //master  send then receive
     sprintf(mailbox, "%d", host_number+1);
     task = MSG_task_create("Token", task_comp_size, task_comm_size, NULL);
index 4df120b..6dde953 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 set(LIBRARY_OUTPUT_PATH "${CMAKE_HOME_DIRECTORY}/lib")
 
index 7e5369a..d2db4d9 100644 (file)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2011, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,7 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 
 if($#ARGV!=0) {
     die "Usage: perl transfrom_optorsim_platform.pl <file.conf>\n";
index 023ffac..048143f 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2011, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,7 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 use Switch;
 my $toversion=3;
 
index 2205650..9f3818e 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2011, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,7 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 use Switch;
 
 my $site="";
index a01bceb..7b530e3 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2011, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,7 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 
 my $toversion=3;
 my $nb_peer = $ARGV[0];
index b3676d2..e2c117f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(tesh_files
   ${tesh_files}
   PARENT_SCOPE
index 7226ae1..138566a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example scala_master_slave_bypass)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/FinalizeTask.scala
index 4880c53..6b014b8 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example scala_master_slave_kill)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/FinalizeTask.scala
index 0e1c2f5..b81f30c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example scala_masterslave)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/FinalizeTask.scala
index e8d50b6..6a1d6d2 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(ex_sd_test sd_test.c)
index 669dd41..56c3b75 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(dax_test dax_test.c)
index aafcab1..545ccf9 100755 (executable)
@@ -1,4 +1,4 @@
-#! /usr/bin/perl
+#! /usr/bin/env perl
 
 # Copyright (c) 2009, 2014. The SimGrid Team.
 # All rights reserved.
index ec59f83..060f899 100755 (executable)
@@ -1,4 +1,4 @@
-#! /usr/bin/perl
+#! /usr/bin/env perl
 
 # Copyright (c) 2009, 2014. The SimGrid Team.
 # All rights reserved.
diff --git a/examples/simdag/dot/.gitignore b/examples/simdag/dot/.gitignore
new file mode 100644 (file)
index 0000000..84e2127
--- /dev/null
@@ -0,0 +1,2 @@
+ptg_test
+dot.dot
index d541688..ae0fc39 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(HAVE_GRAPHVIZ)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
index 4c43abb..2747c19 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(goal_test goal_test.c)
index 6288f7f..0a72b1f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(sd_io sd_io.c)
index b08db6d..05fd01e 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(sd_meta sd_meta.c)
index 833a9fc..d88149f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(sd_prop sd_prop.c)
index c562c14..c141076 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(minmin_test minmin_test.c)
index 2119015..ddd72c8 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index bac394d..ea5eac3 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   set(CMAKE_C_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpicc")
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
index c6efd6e..c66c597 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 6fd67a1..5a3970d 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND SMPI_FORTRAN)
   set(CMAKE_Fortran_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpiff")
 
index 9187792..5d139c1 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND SMPI_FORTRAN)
   set(CMAKE_Fortran_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpif90")
 
diff --git a/examples/smpi/mc/.gitignore b/examples/smpi/mc/.gitignore
new file mode 100644 (file)
index 0000000..daf627a
--- /dev/null
@@ -0,0 +1,5 @@
+smpi_non_termination1
+smpi_non_termination2
+smpi_non_termination3
+smpi_non_termination4
+smpi_only_send_deterministic
index 4897cc7..b0f36ce 100644 (file)
@@ -11,7 +11,7 @@
 /******************************************************************************/
 
 /* Run :
-  /usr/bin/time -f "clock:%e user:%U sys:%S swapped:%W exitval:%x max:%Mk" "$@" ../../../smpi_script/bin/smpirun -hostfile hostfile_bugged1_liveness -platform ../../platforms/cluster.xml --cfg=model-check:1 --cfg=contexts/factory:ucontext --cfg=model-check/reduction:none --cfg=model-check/property:promela_bugged1_liveness --cfg=smpi/send_is_detached_thres:0 --cfg=contexts/stack_size:128 --cfg=model-check/visited:100000 --cfg=model-check/max_depth:100000 ./bugged1_liveness */
+  /usr/bin/time -f "clock:%e user:%U sys:%S swapped:%W exitval:%x max:%Mk" "$@" ../../../smpi_script/bin/smpirun -hostfile hostfile_bugged1_liveness -platform ../../platforms/cluster.xml --cfg=contexts/factory:ucontext --cfg=model-check/reduction:none --cfg=model-check/property:promela_bugged1_liveness --cfg=smpi/send_is_detached_thres:0 --cfg=contexts/stack_size:128 --cfg=model-check/visited:100000 --cfg=model-check/max_depth:100000 ./bugged1_liveness */
 
 #include <stdio.h>
 #include <mpi.h>
index 752393a..a5d8e62 100644 (file)
@@ -1,7 +1,7 @@
 #! ./tesh
 
 ! timeout 60
-$ ../../../smpi_script/bin/smpirun -wrapper ${bindir:=.}/../../../bin/simgrid-mc -hostfile ${srcdir:=.}/hostfile_non_deterministic  -platform ${srcdir:=.}/../../platforms/cluster.xml --log=xbt_cfg.thresh:warning --cfg=model-check:1 --cfg=model-check/communications_determinism:1 --cfg=smpi/send_is_detached_thres:0 --cfg=smpi/running_power:1e9 ./smpi_non_deterministic
+$ ../../../smpi_script/bin/smpirun -wrapper ${bindir:=.}/../../../bin/simgrid-mc -hostfile ${srcdir:=.}/hostfile_non_deterministic  -platform ${srcdir:=.}/../../platforms/cluster.xml --log=xbt_cfg.thresh:warning --cfg=model-check/communications_determinism:1 --cfg=smpi/send_is_detached_thres:0 --cfg=smpi/running_power:1e9 ./smpi_non_deterministic
 > [0.000000] [mc_global/INFO] Check communication determinism
 > [0.000000] [mc_comm_determinism/INFO] The communications pattern of the process 1 is different! (Different communication : 1)
 > [0.000000] [mc_comm_determinism/INFO] ****************************************************
index cbde72f..fa4215f 100644 (file)
@@ -1,4 +1,4 @@
-/* ../../../smpi_script/bin/smpirun -hostfile hostfile_send_deterministic -platform ../../platforms/cluster.xml -np 3 --cfg=model-check:1 --cfg=smpi/send_is_detached_thres:0 gdb\ --args\ ./send_deterministic */
+/* ../../../smpi_script/bin/smpirun -hostfile hostfile_send_deterministic -platform ../../platforms/cluster.xml -np 3 --cfg=smpi/send_is_detached_thres:0 gdb\ --args\ ./send_deterministic */
 
 /* Copyright (c) 2009-2015. The SimGrid Team.
  * All rights reserved.                                                     */
index c315df9..daab716 100644 (file)
@@ -1,7 +1,7 @@
 #! ./tesh
 
 ! timeout 60
-$ ../../../smpi_script/bin/smpirun -wrapper "${bindir:=.}/../../../bin/simgrid-mc" --log=xbt_cfg.thresh:warning -hostfile ${srcdir:=.}/hostfile_only_send_deterministic  -platform ${srcdir:=.}/../../platforms/cluster.xml --cfg=model-check:1 --cfg=model-check/communications_determinism:1 --cfg=smpi/send_is_detached_thres:0 --cfg=smpi/running_power:1e9 ./smpi_only_send_deterministic
+$ ../../../smpi_script/bin/smpirun -wrapper "${bindir:=.}/../../../bin/simgrid-mc" --log=xbt_cfg.thresh:warning -hostfile ${srcdir:=.}/hostfile_only_send_deterministic  -platform ${srcdir:=.}/../../platforms/cluster.xml --cfg=model-check/communications_determinism:1 --cfg=smpi/send_is_detached_thres:0 --cfg=smpi/running_power:1e9 ./smpi_only_send_deterministic
 > [0.000000] [mc_comm_determinism/INFO] Check communication determinism
 > [0.000000] [mc_global/INFO] ******************************************************
 > [0.000000] [mc_global/INFO] **** Only-send-deterministic communication pattern ****
index 2f9afa5..513e1c5 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
   include_directories(BEFORE "${CMAKE_HOME_DIRECTORY}/include/smpi")
index 0b1a1df..241f0f5 100644 (file)
@@ -3,6 +3,7 @@ p Test the replay with multiple instances
 p first generate the deployment file
 $ ${srcdir:=.}/generate_multiple_deployment.sh -platform ${srcdir:=.}/../../platforms/small_platform_with_routers.xml -hostfile ${srcdir:=.}/../hostfile  ${srcdir:=.}/description_file deployment.xml
 
+! timeout 120
 $ ./replay_multiple description_file ${srcdir:=.}/../../platforms/small_platform_with_routers.xml deployment.xml --log=smpi.:info
 > [0.000000] [msg_test/INFO] Initializing instance 1 of size 32
 > [0.000000] [msg_test/INFO] Initializing instance 2 of size 32
index 0c42986..3a16222 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
   include_directories(BEFORE "${CMAKE_HOME_DIRECTORY}/include/smpi")
index 3f704d6..d5681b9 100644 (file)
@@ -113,10 +113,10 @@ int alltoall_mpi(int argc, char *argv[])
 int slave(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   int id = -1;
   char mailbox[80];
-  _XBT_GNUC_UNUSED int read;
+  XBT_ATTRIB_UNUSED int read;
 
   read = sscanf(argv[1], "%d", &id);
   xbt_assert(read, "Invalid argument %s\n", argv[1]);
index 770a426..4538f56 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(tesh_files
   ${tesh_files}
   PARENT_SCOPE
index ada2233..4015e9a 100644 (file)
@@ -30,8 +30,8 @@ XBT_PUBLIC(int) MC_random(int min, int max);
 /* Internal variable used to check if we're running under the MC
  *
  * Please don't use directly: you should use MC_is_active. */
-extern int _sg_do_model_check;
-extern int _sg_mc_visited;
+extern XBT_PUBLIC(int) _sg_do_model_check;
+extern XBT_PUBLIC(int) _sg_mc_visited;
 
 #define MC_is_active()                  _sg_do_model_check
 #define MC_visited_reduction()          _sg_mc_visited
index cec06b7..bd4a8d8 100644 (file)
@@ -52,6 +52,7 @@ typedef struct s_msg_host_priv {
   int        is_migrating;
 
   xbt_dict_t affinity_mask_db;
+  xbt_dynar_t file_descriptor_table;
 
 #ifdef MSG_USE_DEPRECATED
   msg_mailbox_t *mailboxes;     /**< the channels  */
@@ -102,6 +103,7 @@ typedef struct msg_file_priv  {
   char* storageId;
   char* storage_type;
   char* content_type;
+  int desc_id;
   void *data;
   simdata_file_t simdata;
 } s_msg_file_priv_t, *msg_file_priv_t;
index 5265002..ba2e972 100644 (file)
        #endif
 #endif
 
+/* Define to 1 if you have the <unistd.h> header file. */
+#cmakedefine HAVE_UNISTD_H @HAVE_UNISTD_H@
+/* Define to 1 if you have the <sys/time.h> header file. */
+#cmakedefine HAVE_SYS_TIME_H @HAVE_SYS_TIME_H@
 
 /* Define to 1 if mmalloc is compiled in. */
 #cmakedefine HAVE_MMALLOC @HAVE_MMALLOC@
index 2a4bd89..a9117e2 100644 (file)
@@ -7,9 +7,15 @@
 #ifndef SMPI_H
 #define SMPI_H
 
+#include <simgrid_config.h>
+#ifdef HAVE_UNISTD_H
 #include <unistd.h>
-#include <stddef.h>
+#endif
+#ifdef HAVE_SYS_TIME_H
 #include <sys/time.h>
+#endif
+
+#include <stddef.h>
 #include <xbt/misc.h>
 #include <xbt/function_types.h>
 
index de4fe26..97dd769 100644 (file)
@@ -26,8 +26,8 @@ XBT_PUBLIC(void) surf_parse_close(void);
 XBT_PUBLIC(void) surf_parse_init_callbacks(void);
 XBT_PUBLIC(void) surf_parse_reset_callbacks(void);
 XBT_PUBLIC(void) surf_parse_free_callbacks(void);
-XBT_PUBLIC(void) surf_parse_error(const char *msg,...) _XBT_GNUC_PRINTF(1,2) _XBT_GNUC_NORETURN;
-XBT_PUBLIC(void) surf_parse_warn(const char *msg,...) _XBT_GNUC_PRINTF(1,2);
+XBT_PUBLIC(void) XBT_ATTRIB_NORETURN surf_parse_error(const char *msg,...) XBT_ATTRIB_PRINTF(1,2);
+XBT_PUBLIC(void) surf_parse_warn(const char *msg,...) XBT_ATTRIB_PRINTF(1,2);
 XBT_PUBLIC(double) surf_parse_get_double(const char *string);
 XBT_PUBLIC(int) surf_parse_get_int(const char *string);
 XBT_PUBLIC(double) surf_parse_get_time(const char *string);
index 33a9130..5675b55 100644 (file)
@@ -12,6 +12,7 @@
 #include <xbt/misc.h>
 #include <xbt/sysdep.h>
 #include <xbt/str.h>
+#include <xbt/file.h>
 #include <xbt/function_types.h>
 
 #include <xbt/asserts.h>
index a42027a..6450412 100644 (file)
@@ -7,11 +7,11 @@
 #ifndef _XBT_AUTOMATON_H
 #define _XBT_AUTOMATON_H
 
-#include <stdlib.h>
-#include <string.h>
 #include <xbt/dynar.h>
 #include <xbt/sysdep.h>
 #include <xbt/graph.h>
+#include <stdlib.h>
+#include <string.h>
 
 SG_BEGIN_DECL()
 
index b3494fa..dcbaca2 100644 (file)
 
 /* Attributes are only in recent versions of GCC */
 #if defined(__GNUC__) && (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ > 4))
-# define _XBT_GNUC_PRINTF( format_idx, arg_idx )    \
+
+/* On MinGW, stdio.h defines __MINGW_PRINTF_FORMAT and __MINGW_SCANF_FORMAT
+   which are the suitable format style (either gnu_printf or ms_printf)
+   depending on which version is available (__USE_MINGW_ANSI_STDIO): */
+#ifdef __MINGW32__
+  #include <stdio.h>
+#endif
+
+#if defined(__MINGW32__) && defined(__MINGW_PRINTF_FORMAT)
+  # define XBT_ATTRIB_PRINTF( format_idx, arg_idx )    \
+     __attribute__((__format__ (__MINGW_PRINTF_FORMAT, format_idx, arg_idx)))
+#else
+  # define XBT_ATTRIB_PRINTF( format_idx, arg_idx )    \
      __attribute__((__format__ (__printf__, format_idx, arg_idx)))
-# define _XBT_GNUC_SCANF( format_idx, arg_idx )     \
+#endif
+
+#if defined(__MINGW32__) && defined(__MINGW_SCANF_FORMAT)
+  # define XBT_ATTRIB_SCANF( format_idx, arg_idx )     \
+         __attribute__((__MINGW_SCANF_FORMAT (__scanf__, format_idx, arg_idx)))
+#else
+  # define XBT_ATTRIB_SCANF( format_idx, arg_idx )     \
          __attribute__((__format__ (__scanf__, format_idx, arg_idx)))
-# define _XBT_GNUC_NORETURN __attribute__((__noreturn__))
-# define _XBT_GNUC_UNUSED  __attribute__((__unused__))
+#endif
+
+# define XBT_ATTRIB_NORETURN __attribute__((__noreturn__))
+# define XBT_ATTRIB_UNUSED  __attribute__((__unused__))
+
 /* Constructor priorities exist since gcc 4.3.  Apparently, they are however not
  * supported on Macs. */
 # if (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3)) && !defined(__APPLE__)
 # endif
 # undef _XBT_NEED_INIT_PRAGMA
 
-#else                           /* !__GNUC__ */
-# define _XBT_GNUC_PRINTF( format_idx, arg_idx )
-# define _XBT_GNUC_SCANF( format_idx, arg_idx )
-# define _XBT_GNUC_NORETURN
-# define _XBT_GNUC_UNUSED
+#elif defined(_MSC_VER) /* Microsoft Visual Thing */
+# define XBT_ATTRIB_PRINTF( format_idx, arg_idx )
+# define XBT_ATTRIB_SCANF( format_idx, arg_idx )
+# define XBT_ATTRIB_NORETURN __declspec(noreturn)
+# define XBT_ATTRIB_UNUSED
+# define _XBT_GNUC_CONSTRUCTOR(prio)
+# define _XBT_GNUC_DESTRUCTOR(prio)
+# define  _XBT_NEED_INIT_PRAGMA 1
+#else
+# define XBT_ATTRIB_PRINTF( format_idx, arg_idx )
+# define XBT_ATTRIB_SCANF( format_idx, arg_idx )
+# define XBT_ATTRIB_NORETURN
+# define XBT_ATTRIB_UNUSED
 # define _XBT_GNUC_CONSTRUCTOR(prio)
 # define _XBT_GNUC_DESTRUCTOR(prio)
 # define  _XBT_NEED_INIT_PRAGMA 1
 
-#endif                          /* !__GNUC__ */
+#endif                          /* gcc or MSVC else */
 
 /* inline and __FUNCTION__ are only in GCC when -ansi is off */
 
@@ -68,7 +97,7 @@
 #        define XBT_INLINE
 #    endif
 #  else
-#     if defined (__VISUALC__)
+#     if defined (_MSC_VER)
 #       define XBT_INLINE __inline
 #     else
 #       define XBT_INLINE  inline
 #  endif /* __cplusplus */
 #endif
 
+#if defined(__GNUC__)
+#   define XBT_ALWAYS_INLINE inline __attribute__ ((always_inline))
+#else
+#   define XBT_ALWAYS_INLINE XBT_INLINE
+#endif
+
+#if defined(__GNUC__)
+#   define XBT_THREAD_LOCAL __thread
+#elif defined(_MSC_VER)
+#   define XBT_THREAD_LOCAL __declspec(thread)
+#else
+#   define XBT_THREAD_LOCAL No thread local on this architecture
+#endif
+
 /* improvable on gcc (by evaluating arguments only once), but wouldn't be portable */
 #ifdef MIN
 # undef MIN
 
 /*
  * Function calling convention (not used for now)
+ * http://unixwiz.net/techtips/win32-callconv.html <-- good documentation
  */
 
 #ifdef _XBT_WIN32
  *     by default.
  *
  *
- * Rational of XBT_EXPORT_NO_IMPORT: (windows-only cruft)
+ * Rational of XBT_EXPORT_NO_IMPORT: (windows-only)
  *   * Symbols which must be exported in the DLL, but not imported from it.
  *
  *   * This is obviously useful for initialized globals (which cannot be
  *     extern or similar).
- *   * This is also used in the log mecanism where a macro creates the
+ *   * This is also used in the log mechanism where a macro creates the
  *     variable automatically. When the macro is called from within SimGrid,
  *     the symbol must be exported, but when called  from within the client
  *     code, it must not try to retrieve the symbol from the DLL since it's
  *      not in there.
  *
- * Rational of XBT_IMPORT_NO_EXPORT: (windows-only cruft)
- *   * Symbols which must be imported from the DLL, but not explicitely
+ * Rational of XBT_IMPORT_NO_EXPORT: (windows-only)
+ *   * Symbols which must be imported from the DLL, but not explicitly
  *     exported from it.
  *
- *   * The root log category is already exported, but not imported explicitely
+ *   * The root log category is already exported, but not imported explicitly
  *     when creating a subcategory since we cannot import the parent category
  *     to deal with the fact that the parent may be in application space, not
  *     DLL space.
 
 
 /* UNIX build */
-#else
+#elif defined(__ELF__) 
+
 #  define XBT_PUBLIC(type)            type
 #  define XBT_EXPORT_NO_IMPORT(type)  type
 #  define XBT_IMPORT_NO_EXPORT(type)  type
 #  define XBT_PUBLIC_DATA(type)       extern type
 #  define XBT_PUBLIC_CLASS            class
 
+#else
+#  define XBT_PUBLIC(type)            __attribute__((visibility("default"))) type
+#  define XBT_EXPORT_NO_IMPORT(type)  __attribute__((visibility("default"))) type
+#  define XBT_IMPORT_NO_EXPORT(type)  __attribute__((visibility("default"))) type
+#  define XBT_PUBLIC_DATA(type)       extern __attribute__((visibility("default"))) type
+#  define XBT_PUBLIC_CLASS            class __attribute__((visibility("default")))
+
 #endif
 
-#ifdef _XBT_WIN32
-#define XBT_INTERNAL
+#ifdef __ELF__
+#define XBT_PRIVATE __attribute__((visibility("hidden")))
 #else
-#define XBT_INTERNAL __attribute__((visibility ("hidden")))
+#define XBT_PRIVATE
+#endif
+
+#ifdef _MSC_VER /* MSVC has no ssize_t, and I fail to use the SSIZE_T declared in BaseTsd.h */
+       #if defined(_WIN64)
+               typedef __int64 ssize_t;
+       #else
+               typedef long ssize_t;
+       #endif
+
+/* Microsoft wants to improve the code quality blah blah blah */
+/* See: https://msdn.microsoft.com/en-us/library/8ef0s5kh.aspx */
+       /* warning C4996: '_strdup': The POSIX name for this item is deprecated. Instead, use the ISO C and C++ conformant name: _strdup. */
+       #define _CRT_NONSTDC_NO_WARNINGS
+       /* warning C4996: 'fopen': This function or variable may be unsafe. Consider using fopen_s instead. */
+       #define _CRT_SECURE_NO_WARNINGS
 #endif
 
 #if !defined (max) && !defined(__cplusplus)
index e2d82d5..57fdd2f 100644 (file)
@@ -11,8 +11,8 @@
 #ifndef _XBT_CONFIG_H_
 #define _XBT_CONFIG_H_
 
-#include <stdarg.h>
 #include "xbt/dynar.h"
+#include <stdarg.h>
 
 SG_BEGIN_DECL()
 
index 37df800..7a3c876 100644 (file)
@@ -124,12 +124,12 @@ XBT_PUBLIC(void) xbt_test_exit(void);
 
 /* test operations */
 XBT_PUBLIC(void) _xbt_test_add(const char *file, int line, const char *fmt,
-                               ...) _XBT_GNUC_PRINTF(3, 4);
+                               ...) XBT_ATTRIB_PRINTF(3, 4);
 XBT_PUBLIC(void) _xbt_test_fail(const char *file, int line,
-                                const char *fmt, ...) _XBT_GNUC_PRINTF(3,
+                                const char *fmt, ...) XBT_ATTRIB_PRINTF(3,
                                                                        4);
 XBT_PUBLIC(void) _xbt_test_log(const char *file, int line, const char *fmt,
-                               ...) _XBT_GNUC_PRINTF(3, 4);
+                               ...) XBT_ATTRIB_PRINTF(3, 4);
 /** @brief Declare that a new test begins (printf-like parameters, describing the test) 
  *  @hideinitializer */
 #define xbt_test_add(...)       _xbt_test_add(__FILE__, __LINE__, __VA_ARGS__)
index 4ca03cc..007926e 100644 (file)
@@ -228,7 +228,7 @@ typedef struct xbt_dynar_s {
 } s_xbt_dynar_t;
 
 static XBT_INLINE void
-_xbt_dynar_cursor_first(const xbt_dynar_t dynar _XBT_GNUC_UNUSED,
+_xbt_dynar_cursor_first(const xbt_dynar_t dynar XBT_ATTRIB_UNUSED,
                         unsigned int *const cursor)
 {
   /* iterating over a NULL dynar is a no-op (but we don't want to have uninitialized counters) */
index c059056..9ae8f84 100644 (file)
@@ -429,7 +429,7 @@ XBT_PUBLIC( void )__xbt_ex_terminate_default(xbt_ex_t * e);
   _throw_ctx->exception.bt_strings = NULL;                              \
   xbt_backtrace_current((xbt_ex_t *)&(_throw_ctx->exception));
 
-#define _THROW(c, v, m)                                        \
+#define _XBT_THROW(c, v, m)                                        \
   do { /* change this sequence into one block */               \
     xbt_running_ctx_t *_throw_ctx = __xbt_running_ctx_fetch(); \
     THROW_PREPARE(_throw_ctx, c, v, m);                        \
@@ -438,11 +438,11 @@ XBT_PUBLIC( void )__xbt_ex_terminate_default(xbt_ex_t * e);
 
 /** @brief Builds and throws an exception
     @hideinitializer */
-#define THROW(c, v)             _THROW(c, v, NULL)
+#define THROW(c, v)             _XBT_THROW(c, v, NULL)
 
 /** @brief Builds and throws an exception with a printf-like formatted message
     @hideinitializer */
-#define THROWF(c, v, ...)       _THROW(c, v, bprintf(__VA_ARGS__))
+#define THROWF(c, v, ...)       _XBT_THROW(c, v, bprintf(__VA_ARGS__))
 
 #define THROW_IMPOSSIBLE \
   THROWF(unknown_error, 0, "The Impossible Did Happen (yet again)")
diff --git a/include/xbt/file.h b/include/xbt/file.h
new file mode 100644 (file)
index 0000000..2b577fb
--- /dev/null
@@ -0,0 +1,41 @@
+/* str.h - XBT string related functions.                                    */
+
+/* Copyright (c) 2007-2015. The SimGrid Team.
+ * All rights reserved.                                                     */
+
+/* This program is free software; you can redistribute it and/or modify it
+ * under the terms of the license (GNU LGPL) which comes with this package. */
+
+#ifndef XBT_FILE_H
+#define XBT_FILE_H
+
+#include <stdint.h> /* ssize_t */
+#include <stdarg.h>             /* va_* */
+#include <stdio.h>  /* FILE */
+#include <stdlib.h> /* size_t, ssize_t */
+#include "xbt/misc.h"
+#include "xbt/dynar.h"
+#include "xbt/dict.h"
+#include "simgrid_config.h"     /* FILE for getline */
+
+SG_BEGIN_DECL()
+
+/** @addtogroup XBT_file
+ *  @brief File manipulation functions
+ *
+ * This module redefine some quite classical functions such as xbt_getline() or xbt_dirname() for the platforms
+ * lacking them.
+ * @{
+ */
+/* Our own implementation of getline, mainly useful on the platforms not enjoying this function */
+XBT_PUBLIC(ssize_t) xbt_getline(char **lineptr, size_t * n, FILE * stream);
+
+/* Our own implementation of dirname, that does not exist on windows */
+XBT_PUBLIC(char *) xbt_dirname(const char *path);
+XBT_PUBLIC(char *) xbt_basename(const char *path);
+
+
+/**@}*/
+
+SG_END_DECL()
+#endif                          /* XBT_FILE_H */
index 68132cf..b53652e 100644 (file)
@@ -191,7 +191,7 @@ typedef enum {
 # define XBT_LOG_DEFAULT_CATEGORY(cname)
 #else
 # define XBT_LOG_DEFAULT_CATEGORY(cname) \
-   static xbt_log_category_t _XBT_LOGV(default) _XBT_GNUC_UNUSED = &_XBT_LOGV(cname)
+   static xbt_log_category_t _XBT_LOGV(default) XBT_ATTRIB_UNUSED = &_XBT_LOGV(cname)
 #endif
 
 /**
@@ -348,7 +348,7 @@ XBT_PUBLIC(xbt_log_appender_t) xbt_log_appender2_file_new(char *arg,int roll);
 /* ********************************** */
 XBT_PUBLIC(void) _xbt_log_event_log(xbt_log_event_t ev,
                                     const char *fmt,
-                                    ...) _XBT_GNUC_PRINTF(2, 3);
+                                    ...) XBT_ATTRIB_PRINTF(2, 3);
 
 XBT_PUBLIC(int) _xbt_log_cat_init(xbt_log_category_t category,
                                   e_xbt_log_priority_t priority);
@@ -395,8 +395,8 @@ extern xbt_log_layout_t xbt_log_default_layout;
  */
 #define _XBT_LOG_ISENABLEDV(catv, priority)                  \
        (priority >= XBT_LOG_STATIC_THRESHOLD                 \
-        && (catv.initialized || _xbt_log_cat_init(&catv, priority)) \
-        && priority >= catv.threshold)
+        && ((catv).initialized || _xbt_log_cat_init(&(catv), priority)) \
+        && priority >= (catv).threshold)
 
 /*
  * Internal Macros
@@ -422,11 +422,28 @@ extern xbt_log_layout_t xbt_log_default_layout;
   fprintf(stderr,"%s:%d:\n" f, __FILE__, __LINE__, __VA_ARGS__)
 # define XBT_LOG(...) XBT_CLOG(0, __VA_ARGS__)
 #else
-# define XBT_CLOG_(catv, prio, ...)                                     \
+
+// This code is duplicated to remove one level of indirection, working around a MSVC bug
+// See: http://stackoverflow.com/questions/9183993/msvc-variadic-macro-expansion
+
+# define XBT_CLOG(category, prio, ...) \
+  do {                                                                  \
+    if (_XBT_LOG_ISENABLEDV((category), prio)) {                        \
+      s_xbt_log_event_t _log_ev;                                        \
+      _log_ev.cat = &(category);                                        \
+      _log_ev.priority = (prio);                                        \
+      _log_ev.fileName = __FILE__;                                      \
+      _log_ev.functionName = _XBT_FUNCTION;                             \
+      _log_ev.lineNum = __LINE__;                                       \
+      _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+    }                                                                   \
+  }  while (0)
+
+# define XBT_LOG(prio,...) \
   do {                                                                  \
-    if (_XBT_LOG_ISENABLEDV(catv, prio)) {                              \
+    if (_XBT_LOG_ISENABLEDV((*_simgrid_log_category__default), prio)) { \
       s_xbt_log_event_t _log_ev;                                        \
-      _log_ev.cat = &(catv);                                            \
+      _log_ev.cat = _simgrid_log_category__default;                     \
       _log_ev.priority = (prio);                                        \
       _log_ev.fileName = __FILE__;                                      \
       _log_ev.functionName = _XBT_FUNCTION;                             \
@@ -434,8 +451,6 @@ extern xbt_log_layout_t xbt_log_default_layout;
       _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
     }                                                                   \
   }  while (0)
-# define XBT_CLOG(cat, prio, ...) XBT_CLOG_(_XBT_LOGV(cat), prio, __VA_ARGS__)
-# define XBT_LOG(...) XBT_CLOG_((*_XBT_LOGV(default)), __VA_ARGS__)
 #endif
 
 /** @ingroup XBT_log
@@ -444,74 +459,214 @@ extern xbt_log_layout_t xbt_log_default_layout;
  * \param ... the format string and its arguments
  *  @brief Log an event at the DEBUG priority on the specified category with these args.
  */
-#define XBT_CDEBUG(c, ...) XBT_CLOG(c, xbt_log_priority_debug, __VA_ARGS__)
+#define XBT_CDEBUG(categ, ...) \
+                 do {                                                                  \
+                   if (XBT_LOG_ISENABLED (categ, xbt_log_priority_debug)) {            \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = &(_XBT_LOGV(categ));                                \
+                     _log_ev.priority = xbt_log_priority_debug;                        \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the VERB priority on the specified category with these args.
  */
-#define XBT_CVERB(c, ...) XBT_CLOG(c, xbt_log_priority_verbose, __VA_ARGS__)
+#define XBT_CVERB(categ, ...)  \
+                 do {                                                                  \
+                   if (XBT_LOG_ISENABLED (categ, xbt_log_priority_verbose)) {          \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = &(_XBT_LOGV(categ));                                \
+                     _log_ev.priority = xbt_log_priority_verbose;                      \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the INFO priority on the specified category with these args.
  */
-#define XBT_CINFO(c, ...) XBT_CLOG(c, xbt_log_priority_info, __VA_ARGS__)
+#define XBT_CINFO(categ, ...) \
+                 do {                                                                  \
+                   if (XBT_LOG_ISENABLED (categ, xbt_log_priority_info)) {             \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = &(_XBT_LOGV(categ));                                \
+                     _log_ev.priority = xbt_log_priority_info;                         \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
+
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the WARN priority on the specified category with these args.
  */
-#define XBT_CWARN(c, ...) XBT_CLOG(c, xbt_log_priority_warning, __VA_ARGS__)
+#define XBT_CWARN(categ, ...) \
+                 do {                                                                  \
+                   if (XBT_LOG_ISENABLED (categ, xbt_log_priority_warning)) {          \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = &(_XBT_LOGV(categ));                                \
+                     _log_ev.priority = xbt_log_priority_warning;                      \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
+
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the ERROR priority on the specified category with these args.
  */
-#define XBT_CERROR(c, ...) XBT_CLOG(c, xbt_log_priority_error, __VA_ARGS__)
+#define XBT_CERROR(categ, ...) \
+                 do {                                                                  \
+                   if (XBT_LOG_ISENABLED (categ, xbt_log_priority_error)) {            \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = &(_XBT_LOGV(categ));                                \
+                     _log_ev.priority = xbt_log_priority_error;                        \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the CRITICAL priority on the specified category with these args (CCRITICALn exists for any n<10).
  */
-#define XBT_CCRITICAL(c, ...) XBT_CLOG(c, xbt_log_priority_critical, __VA_ARGS__)
+#define XBT_CCRITICAL(categ, ...) \
+                 do {                                                                  \
+                   if (XBT_LOG_ISENABLED (categ, xbt_log_priority_critical)) {         \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = &(_XBT_LOGV(categ));                                \
+                     _log_ev.priority = xbt_log_priority_critical;                     \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  * \param ... the format string and its arguments
  *  @brief Log an event at the DEBUG priority on the default category with these args.
  */
-#define XBT_DEBUG(...) XBT_LOG(xbt_log_priority_debug, __VA_ARGS__)
+#define XBT_DEBUG(...) \
+                 do {                                                                  \
+                   if (_XBT_LOG_ISENABLEDV(*_simgrid_log_category__default,            \
+                                               xbt_log_priority_debug)) {                  \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = _simgrid_log_category__default;                     \
+                     _log_ev.priority = xbt_log_priority_debug;                        \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the VERB priority on the default category with these args.
  */
-#define XBT_VERB(...) XBT_LOG(xbt_log_priority_verbose, __VA_ARGS__)
+#define XBT_VERB(...) \
+                 do {                                                                  \
+                   if (_XBT_LOG_ISENABLEDV(*_simgrid_log_category__default,            \
+                                               xbt_log_priority_verbose)) {                \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = _simgrid_log_category__default;                     \
+                     _log_ev.priority = xbt_log_priority_verbose;                      \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the INFO priority on the default category with these args.
  */
-#define XBT_INFO(...) XBT_LOG(xbt_log_priority_info, __VA_ARGS__)
+#define XBT_INFO(...) \
+                 do {                                                                  \
+                   if (_XBT_LOG_ISENABLEDV(*_simgrid_log_category__default,            \
+                                               xbt_log_priority_info)) {                   \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = _simgrid_log_category__default;                     \
+                     _log_ev.priority = xbt_log_priority_info;                         \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the WARN priority on the default category with these args.
  */
-#define XBT_WARN(...) XBT_LOG(xbt_log_priority_warning, __VA_ARGS__)
+#define XBT_WARN(...) \
+                 do {                                                                  \
+                   if (_XBT_LOG_ISENABLEDV(*_simgrid_log_category__default,            \
+                                               xbt_log_priority_warning)) {                \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = _simgrid_log_category__default;                     \
+                     _log_ev.priority = xbt_log_priority_warning;                      \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the ERROR priority on the default category with these args.
  */
-#define XBT_ERROR(...) XBT_LOG(xbt_log_priority_error, __VA_ARGS__)
+#define XBT_ERROR(...) \
+                 do {                                                                  \
+                   if (_XBT_LOG_ISENABLEDV(*_simgrid_log_category__default,            \
+                                               xbt_log_priority_error)) {                  \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = _simgrid_log_category__default;                     \
+                     _log_ev.priority = xbt_log_priority_error;                        \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 /** @ingroup XBT_log
  *  @hideinitializer
  *  @brief Log an event at the CRITICAL priority on the default category with these args.
  */
-#define XBT_CRITICAL(...) XBT_LOG(xbt_log_priority_critical, __VA_ARGS__)
+#define XBT_CRITICAL(...) \
+                 do {                                                                  \
+                   if (_XBT_LOG_ISENABLEDV(*_simgrid_log_category__default,            \
+                                               xbt_log_priority_critical)) {               \
+                     s_xbt_log_event_t _log_ev;                                        \
+                     _log_ev.cat = _simgrid_log_category__default;                     \
+                     _log_ev.priority = xbt_log_priority_critical;                     \
+                     _log_ev.fileName = __FILE__;                                      \
+                     _log_ev.functionName = _XBT_FUNCTION;                             \
+                     _log_ev.lineNum = __LINE__;                                       \
+                     _xbt_log_event_log(&_log_ev, __VA_ARGS__);                        \
+                   }                                                                   \
+                 }  while (0)
 
 #define _XBT_IN_OUT(...) \
   _XBT_IF_ONE_ARG(_XBT_IN_OUT_ARG1, _XBT_IN_OUT_ARGN, __VA_ARGS__)(__VA_ARGS__)
index afbe273..e1e454b 100644 (file)
@@ -9,12 +9,12 @@
 #ifndef XBT_MISC_H
 #define XBT_MISC_H
 
-#include <stdarg.h>
-
 #include "simgrid_config.h"
 #include "base.h"
 #include "dynar.h"
 
+#include <stdarg.h>
+
 SG_BEGIN_DECL()
 
 /** Cache the size of a memory page for the current system. */
@@ -51,7 +51,7 @@ XBT_PUBLIC_DATA(xbt_dynar_t) sg_cmdline;
  */
 #if defined(SIMGRID_NEED_ASPRINTF)||defined(DOXYGEN)
 XBT_PUBLIC(int) asprintf(char **ptr, const char *fmt,   /*args */
-                         ...) _XBT_GNUC_PRINTF(2, 3);
+                         ...) XBT_ATTRIB_PRINTF(2, 3);
 #endif
 /** @brief print to allocated string (reimplemented when not provided by the system)
  *
@@ -72,7 +72,7 @@ XBT_PUBLIC(char *) bvprintf(const char *fmt, va_list ap);
  * Works just like asprintf(), but returns a pointer to the newly
  * created string, or aborts on error.
  */
-XBT_PUBLIC(char *) bprintf(const char *fmt, ...) _XBT_GNUC_PRINTF(1, 2);
+XBT_PUBLIC(char *) bprintf(const char *fmt, ...) XBT_ATTRIB_PRINTF(1, 2);
 /** @} */
 
 SG_END_DECL()
index 3307ed7..3fb53d2 100644 (file)
@@ -9,27 +9,27 @@
 #ifndef XBT_STR_H
 #define XBT_STR_H
 
-#include <stdint.h> /* ssize_t */
-#include <stdarg.h>             /* va_* */
 #include "xbt/misc.h"
 #include "xbt/dynar.h"
 #include "xbt/dict.h"
-#include "simgrid_config.h"     /* FILE for getline */
+
+#include <stdarg.h>             /* va_* */
+#include <stdio.h>  /* FILE */
+
+#ifdef _MSC_VER
+#define strcasecmp _stricmp
+#endif
 
 SG_BEGIN_DECL()
 
 /** @addtogroup XBT_str
  *  @brief String manipulation functions
  *
- * This module defines several string related functions. We redefine some quite classical
- * functions on the platforms were they are not nativaly defined (such as xbt_getline() or
- * asprintf()), while some other are a bit more exotic.
+ * This module defines several string related functions. Looking at the diversity of string
+ * manipulation functions that are provided, you can see that several SimGrid core developers
+ * actually like Perl.
  * @{
  */
-/* Our own implementation of getline, mainly useful on the platforms not enjoying this function */
-#include <stdio.h>  /* FILE */
-#include <stdlib.h> /* size_t, ssize_t */
-XBT_PUBLIC(ssize_t) xbt_getline(char **lineptr, size_t * n, FILE * stream);
 
 /* Trim related functions */
 XBT_PUBLIC(void) xbt_str_rtrim(char *s, const char *char_list);
index 9ed7c53..4e407ab 100644 (file)
@@ -35,7 +35,7 @@ SG_BEGIN_DECL()
  * @{
  */
 /** @brief Kill the program in silence */
-XBT_PUBLIC(void) xbt_abort(void) _XBT_GNUC_NORETURN;
+XBT_PUBLIC(void) XBT_ATTRIB_NORETURN xbt_abort(void);
 
 /**
  * @brief Kill the program with an error message
@@ -54,16 +54,20 @@ XBT_PUBLIC(void) xbt_abort(void) _XBT_GNUC_NORETURN;
   } while (0)
 /** @} */
 
+#ifdef XBT_LOG_LOCALLY_DEFINE_XBT_CHANNEL
+XBT_LOG_NEW_CATEGORY(xbt, "All XBT categories (simgrid toolbox)");
+#else
 XBT_LOG_EXTERNAL_CATEGORY(xbt);
+#endif
 
 /* these ones live in str.h, but redeclare them here so that we do
    not need to load the whole str.h and its heavy dependencies */
 #ifndef __USE_GNU               /* do not redeclare existing headers */
 XBT_PUBLIC(int) asprintf(char **ptr, const char *fmt,   /*args */
-                         ...) _XBT_GNUC_PRINTF(2, 3);
+                         ...) XBT_ATTRIB_PRINTF(2, 3);
 XBT_PUBLIC(int) vasprintf(char **ptr, const char *fmt, va_list ap);
 #endif
-XBT_PUBLIC(char *) bprintf(const char *fmt, ...) _XBT_GNUC_PRINTF(1, 2);
+XBT_PUBLIC(char *) bprintf(const char *fmt, ...) XBT_ATTRIB_PRINTF(1, 2);
 
 /** @addtogroup XBT_syscall
  *  @brief Malloc and associated functions, killing the program on error (with \ref XBT_ex)
@@ -71,11 +75,12 @@ XBT_PUBLIC(char *) bprintf(const char *fmt, ...) _XBT_GNUC_PRINTF(1, 2);
  *  @{
  */
 
-#if defined(__GNUC__) || defined(DOXYGEN)
+#if defined(_MSC_VER) && !defined(strdup)
+#  define strdup _strdup /* POSIX name is not ANSI complient blabla */
+#endif
+
 /** @brief Like strdup, but xbt_die() on error */
-static inline __attribute__ ((always_inline))
-char *xbt_strdup(const char *s)
-{
+static XBT_ALWAYS_INLINE char *xbt_strdup(const char *s) {
   char *res = NULL;
   if (s) {
     res = strdup(s);
@@ -89,9 +94,7 @@ XBT_PUBLIC(void) xbt_backtrace_display_current(void);
 
 /** @brief Like malloc, but xbt_die() on error
     @hideinitializer */
-static inline __attribute__ ((always_inline))
-void *xbt_malloc(size_t n)
-{
+static XBT_ALWAYS_INLINE void *xbt_malloc(size_t n) {
   void *res;
 /*  if (n==0) {
      xbt_backtrace_display_current();
@@ -106,9 +109,7 @@ void *xbt_malloc(size_t n)
 
 /** @brief like malloc, but xbt_die() on error and memset data to 0
     @hideinitializer */
-static inline __attribute__ ((always_inline))
-void *xbt_malloc0(size_t n)
-{
+static XBT_ALWAYS_INLINE void *xbt_malloc0(size_t n) {
   void *res;
   //if (n==0) xbt_die("calloc(0) is not portable");
   res = calloc(n, 1);
@@ -119,9 +120,7 @@ void *xbt_malloc0(size_t n)
 
 /** @brief like realloc, but xbt_die() on error
     @hideinitializer */
-static inline __attribute__ ((always_inline))
-void *xbt_realloc(void *p, size_t s)
-{
+static XBT_ALWAYS_INLINE void *xbt_realloc(void *p, size_t s) {
   void *res = NULL;
   //if (s==0) xbt_die("realloc(0) is not portable");
   if (s) {
@@ -137,12 +136,6 @@ void *xbt_realloc(void *p, size_t s)
   }
   return res;
 }
-#else                           /* non __GNUC__  */
-#  define xbt_strdup(s)    strdup(s)
-#  define xbt_malloc(n)    malloc(n)
-#  define xbt_malloc0(n)   calloc(n,1)
-#  define xbt_realloc(p,s) realloc(p,s)
-#endif                          /* __GNUC__ ? */
 
 /** @brief like free
     @hideinitializer */
index 72ae279..3c336cb 100644 (file)
@@ -27,7 +27,7 @@ typedef struct xbt_os_thread_ *xbt_os_thread_t;
 
 
 #ifdef _XBT_WIN32 /* defined if this is a windows system, 32bits or 64bits) */
-#include <windef.h>
+#include <windows.h>
 typedef DWORD xbt_os_thread_key_t;
 #else /* assume that every non-windows system is POSIX-compatible */
 
index fc7cbba..bb1ca2b 100644 (file)
@@ -1,4 +1,3 @@
-Manifest-Version: 1.0
 Built-By: Da SimGrid team
 Main-Class: org.simgrid.msg.Msg
 Class-Path: .
index 599ea7a..85dbcb3 100644 (file)
@@ -34,11 +34,11 @@ void jas_unref(JNIEnv * env, jobject jas) {
 }
 
 void jas_bind(jobject jas, msg_as_t as, JNIEnv * env) {
-  (*env)->SetLongField(env, jas, jas_field_As_bind, (jlong) (long) (as));
+  (*env)->SetLongField(env, jas, jas_field_As_bind, (jlong) (uintptr_t) (as));
 }
 
 msg_as_t jas_get_native(JNIEnv * env, jobject jas) {
-  return (msg_as_t) (long) (*env)->GetLongField(env, jas, jas_field_As_bind);
+  return (msg_as_t) (uintptr_t) (*env)->GetLongField(env, jas, jas_field_As_bind);
 }
 
 JNIEXPORT void JNICALL
index de3cf7b..061a528 100644 (file)
@@ -20,7 +20,7 @@ static jfieldID jtask_field_Comm_task;
 static jfieldID jcomm_field_Comm_taskBind;
 
 void jcomm_bind_task(JNIEnv *env, jobject jcomm) {
-  msg_comm_t comm = (msg_comm_t) (long) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
+  msg_comm_t comm = (msg_comm_t) (uintptr_t) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
   //test if we are receiving or sending a task.
   jboolean jreceiving = (*env)->GetBooleanField(env, jcomm, jcomm_field_Comm_receiving);
   if (jreceiving == JNI_TRUE) {
@@ -66,17 +66,17 @@ Java_org_simgrid_msg_Comm_nativeFinalize(JNIEnv *env, jobject jcomm) {
   msg_comm_t comm;
   msg_task_t *task_received;
 
-  task_received = (msg_task_t*)  (long) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_taskBind);
+  task_received = (msg_task_t*)  (uintptr_t) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_taskBind);
   xbt_free(task_received);
 
-  comm = (msg_comm_t) (long) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
+  comm = (msg_comm_t) (uintptr_t) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
   MSG_comm_destroy(comm);
 }
 
 JNIEXPORT jboolean JNICALL
 Java_org_simgrid_msg_Comm_test(JNIEnv *env, jobject jcomm) {
   msg_comm_t comm;
-  comm = (msg_comm_t) (long) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
+  comm = (msg_comm_t) (uintptr_t) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
 
   jboolean finished = (*env)->GetBooleanField(env, jcomm, jcomm_field_Comm_finished);
   if (finished == JNI_TRUE) {
@@ -102,7 +102,7 @@ Java_org_simgrid_msg_Comm_test(JNIEnv *env, jobject jcomm) {
 }
 JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Comm_waitCompletion(JNIEnv *env, jobject jcomm, jdouble timeout) {
-  msg_comm_t comm = (msg_comm_t) (long) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
+  msg_comm_t comm = (msg_comm_t) (uintptr_t) (*env)->GetLongField(env, jcomm, jcomm_field_Comm_bind);
   if (!comm) {
     jxbt_throw_native(env,bprintf("comm is null"));
     return;
index a64a831..4b82931 100644 (file)
@@ -34,11 +34,11 @@ void jhost_unref(JNIEnv * env, jobject jhost) {
 }
 
 void jhost_bind(jobject jhost, msg_host_t host, JNIEnv * env) {
-  (*env)->SetLongField(env, jhost, jhost_field_Host_bind, (jlong) (long) (host));
+  (*env)->SetLongField(env, jhost, jhost_field_Host_bind, (jlong) (uintptr_t) (host));
 }
 
 msg_host_t jhost_get_native(JNIEnv * env, jobject jhost) {
-  return (msg_host_t) (long) (*env)->GetLongField(env, jhost, jhost_field_Host_bind);
+  return (msg_host_t) (uintptr_t) (*env)->GetLongField(env, jhost, jhost_field_Host_bind);
 }
 
 const char *jhost_get_name(jobject jhost, JNIEnv * env) {
index 8b24343..d3fd8db 100644 (file)
@@ -24,7 +24,7 @@ jobject jstorage_new_instance(JNIEnv * env) {
 }
 
 msg_storage_t jstorage_get_native(JNIEnv * env, jobject jstorage) {
-  return (msg_storage_t) (long) (*env)->GetLongField(env, jstorage, jstorage_field_Storage_bind);
+  return (msg_storage_t) (uintptr_t) (*env)->GetLongField(env, jstorage, jstorage_field_Storage_bind);
 }
 
 JNIEXPORT void JNICALL
@@ -39,7 +39,7 @@ Java_org_simgrid_msg_Storage_nativeInit(JNIEnv *env, jclass cls) {
 }
 
 void jstorage_bind(jobject jstorage, msg_storage_t storage, JNIEnv * env) {
-  (*env)->SetLongField(env, jstorage, jstorage_field_Storage_bind, (jlong) (long) (storage));
+  (*env)->SetLongField(env, jstorage, jstorage_field_Storage_bind, (jlong) (uintptr_t) (storage));
 }
 
 jobject jstorage_ref(JNIEnv * env, jobject jstorage) {
index fc43650..23d1fd2 100644 (file)
@@ -26,14 +26,14 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Mutex_init(JNIEnv * env, jobject obj) {
   xbt_mutex_t mutex = xbt_mutex_init();
 
-  (*env)->SetLongField(env, obj, jsyncro_field_Mutex_bind, (jlong) (long) (mutex));
+  (*env)->SetLongField(env, obj, jsyncro_field_Mutex_bind, (jlong) (uintptr_t) (mutex));
 }
 
 JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Mutex_acquire(JNIEnv * env, jobject obj) {
   xbt_mutex_t mutex;
 
-  mutex = (xbt_mutex_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Mutex_bind);
+  mutex = (xbt_mutex_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Mutex_bind);
   xbt_ex_t e;
   TRY {
     xbt_mutex_acquire(mutex);
@@ -47,7 +47,7 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Mutex_release(JNIEnv * env, jobject obj) {
   xbt_mutex_t mutex;
 
-  mutex = (xbt_mutex_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Mutex_bind);
+  mutex = (xbt_mutex_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Mutex_bind);
   xbt_mutex_release(mutex);
 }
 
@@ -55,7 +55,7 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Mutex_nativeFinalize(JNIEnv * env, jobject obj) {
   xbt_mutex_t mutex;
 
-  mutex = (xbt_mutex_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Mutex_bind);
+  mutex = (xbt_mutex_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Mutex_bind);
   xbt_mutex_destroy(mutex);
 }
 
@@ -72,7 +72,7 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Semaphore_init(JNIEnv * env, jobject obj, jint capacity) {
   msg_sem_t sem = MSG_sem_init((int) capacity);
 
-  (*env)->SetLongField(env, obj, jsyncro_field_Semaphore_bind, (jlong) (long) (sem));
+  (*env)->SetLongField(env, obj, jsyncro_field_Semaphore_bind, (jlong) (uintptr_t) (sem));
 }
 
 
@@ -80,7 +80,7 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Semaphore_acquire(JNIEnv * env, jobject obj, jdouble timeout) {
   msg_sem_t sem;
 
-  sem = (msg_sem_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
+  sem = (msg_sem_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
   msg_error_t res = MSG_sem_acquire_timeout(sem, (double) timeout);
   if (res != MSG_OK) {
     jmsg_throw_status(env, res);
@@ -91,14 +91,14 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Semaphore_release(JNIEnv * env, jobject obj) {
   msg_sem_t sem;
 
-  sem = (msg_sem_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
+  sem = (msg_sem_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
   MSG_sem_release(sem);
 }
 JNIEXPORT jboolean JNICALL
 Java_org_simgrid_msg_Semaphore_wouldBlock(JNIEnv * env, jobject obj) {
   msg_sem_t sem;
 
-  sem = (msg_sem_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
+  sem = (msg_sem_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
   int res = MSG_sem_would_block(sem);
   return (jboolean) res;
 }
@@ -107,6 +107,6 @@ JNIEXPORT void JNICALL
 Java_org_simgrid_msg_Semaphore_nativeFinalize(JNIEnv * env, jobject obj) {
   msg_sem_t sem;
 
-  sem = (msg_sem_t) (long) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
+  sem = (msg_sem_t) (uintptr_t) (*env)->GetLongField(env, obj, jsyncro_field_Semaphore_bind);
   MSG_sem_destroy(sem);
 }
index b2ecd2e..b8048f0 100644 (file)
@@ -482,8 +482,8 @@ Java_org_simgrid_msg_Task_irecv(JNIEnv * env, jclass cls, jstring jmailbox) {
 
        comm = MSG_task_irecv(task,mailbox);
 
-       (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (long)(comm));
-       (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (long)(task));
+       (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (uintptr_t)(comm));
+       (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (uintptr_t)(task));
        (*env)->SetBooleanField(env, jcomm, jtask_field_Comm_receiving, JNI_TRUE);
 
        (*env)->ReleaseStringUTFChars(env, jmailbox, mailbox);
@@ -564,8 +564,8 @@ Java_org_simgrid_msg_Task_irecvBounded(JNIEnv * env, jclass cls,
 
        comm = MSG_task_irecv_bounded(task,mailbox, (double) rate);
 
-       (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (long)(comm));
-       (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (long)(task));
+       (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (uintptr_t)(comm));
+       (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (uintptr_t)(task));
        (*env)->SetBooleanField(env, jcomm, jtask_field_Comm_receiving, JNI_TRUE);
 
        (*env)->ReleaseStringUTFChars(env, jmailbox, mailbox);
@@ -603,8 +603,8 @@ Java_org_simgrid_msg_Task_isend(JNIEnv *env, jobject jtask, jstring jmailbox) {
 MSG_task_set_data(task, (void *) (*env)->NewGlobalRef(env, jtask));
   comm = MSG_task_isend(task,mailbox);
 
-  (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (long)(comm));
-  (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (long)(NULL));
+  (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (uintptr_t)(comm));
+  (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (uintptr_t)(NULL));
   (*env)->SetBooleanField(env, jcomm, jtask_field_Comm_receiving, JNI_FALSE);
 
   (*env)->ReleaseStringUTFChars(env, jmailbox, mailbox);
@@ -642,8 +642,8 @@ Java_org_simgrid_msg_Task_isendBounded(JNIEnv *env, jobject jtask, jstring jmail
 MSG_task_set_data(task, (void *) (*env)->NewGlobalRef(env, jtask));
   comm = MSG_task_isend_bounded(task,mailbox,maxrate);
 
-  (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (long)(comm));
-  (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (long)(NULL));
+  (*env)->SetLongField(env, jcomm, jtask_field_Comm_bind, (jlong) (uintptr_t)(comm));
+  (*env)->SetLongField(env, jcomm, jtask_field_Comm_taskBind, (jlong) (uintptr_t)(NULL));
   (*env)->SetBooleanField(env, jcomm, jtask_field_Comm_receiving, JNI_FALSE);
 
   (*env)->ReleaseStringUTFChars(env, jmailbox, mailbox);
index 7a4fecf..6bd5dae 100644 (file)
@@ -10,30 +10,25 @@ import java.io.FileOutputStream;
 import java.io.InputStream;
 import java.io.OutputStream;
 import java.io.File;
+import java.nio.file.Files;
+import java.nio.file.Path;
 
 public final class NativeLib {
-
-       public static String getPath() {
-               String prefix = "NATIVE";
-               String os = System.getProperty("os.name");
-               String arch = System.getProperty("os.arch");
-
-               if (arch.matches("^i[3-6]86$"))
-                       arch = "x86";
-               else if (arch.equalsIgnoreCase("amd64"))
-                       arch = "x86_64";
-
-               if (os.toLowerCase().startsWith("win")){
-                       os = "Windows";
-                       arch = "x86";
-               }else if (os.contains("OS X"))
-                       os = "Darwin";
-
-               os = os.replace(' ', '_');
-               arch = arch.replace(' ', '_');
-
-               return prefix + "/" + os + "/" + arch + "/";
+       /* Statically load the library which contains all native functions used in here */
+       static private boolean isNativeInited = false;
+       public static void nativeInit() {
+               if (isNativeInited)
+                       return;
+               
+               if (System.getProperty("os.name").toLowerCase().startsWith("win"))
+                       NativeLib.nativeInit("winpthread-1");
+
+               NativeLib.nativeInit("simgrid");
+               NativeLib.nativeInit("surf-java");
+               NativeLib.nativeInit("simgrid-java");      
+               isNativeInited = true;
        }
+
        public static void nativeInit(String name) {
                try {
                        /* Prefer the version of the library bundled into the jar file and use it */
@@ -51,6 +46,30 @@ public final class NativeLib {
                }
        }
 
+       public static String getPath() {
+               // Inspiration: https://github.com/xerial/snappy-java/blob/develop/src/main/java/org/xerial/snappy/OSInfo.java
+               String prefix = "NATIVE";
+               String os = System.getProperty("os.name");
+               String arch = System.getProperty("os.arch");
+
+               if (arch.matches("^i[3-6]86$"))
+                       arch = "x86";
+               else if (arch.equalsIgnoreCase("x86_64"))
+                       arch = "amd64";
+               else if (arch.equalsIgnoreCase("AMD64"))
+                       arch = "amd64";
+
+               if (os.toLowerCase().startsWith("win")){
+                       os = "Windows";
+               } else if (os.contains("OS X"))
+                       os = "Darwin";
+
+               os = os.replace(' ', '_');
+               arch = arch.replace(' ', '_');
+
+               return prefix + "/" + os + "/" + arch + "/";
+       }
+       static Path tempDir = null;
        private static void loadLib (String name) throws SimGridLibNotFoundException {
                String Path = NativeLib.getPath();
 
@@ -60,31 +79,33 @@ public final class NativeLib {
                if (in == null) {
                        filename = "lib"+name+".so";
                        in = NativeLib.class.getClassLoader().getResourceAsStream(Path+filename);
-               } 
+               }
                if (in == null) {
                        filename = name+".dll";
                        in =  NativeLib.class.getClassLoader().getResourceAsStream(Path+filename);
-               }  
+               }
                if (in == null) {
                        filename = "lib"+name+".dll";
                        in =  NativeLib.class.getClassLoader().getResourceAsStream(Path+filename);
-               }  
+               }
                if (in == null) {
                        filename = "lib"+name+".dylib";
                        in =  NativeLib.class.getClassLoader().getResourceAsStream(Path+filename);
-               }  
+               }
                if (in == null) {
                        throw new SimGridLibNotFoundException("Cannot find library "+name+" in path "+Path+". Sorry, but this jar does not seem to be usable on your machine.");
                }
                try {
                        // We must write the lib onto the disk before loading it -- stupid operating systems
-                       File fileOut = new File(filename);
-                       fileOut = File.createTempFile(name+"-", ".tmp");
-                       // don't leak the file on disk, but remove it on JVM shutdown
-                       Runtime.getRuntime().addShutdownHook(new Thread(new FileCleaner(fileOut.getAbsolutePath())));
-                       OutputStream out = new FileOutputStream(fileOut);
+                       if (tempDir == null) {
+                               tempDir = Files.createTempDirectory("simgrid-java");
+                               // don't leak the files on disk, but remove it on JVM shutdown
+                               Runtime.getRuntime().addShutdownHook(new Thread(new FileCleaner(tempDir.toFile())));
+                       }
+                       File fileOut = new File(tempDir.toFile().getAbsolutePath() + File.separator + filename);
 
                        /* copy the library in position */  
+                       OutputStream out = new FileOutputStream(fileOut);
                        byte[] buffer = new byte[4096]; 
                        int bytes_read; 
                        while ((bytes_read = in.read(buffer)) != -1)     // Read until EOF
@@ -94,23 +115,26 @@ public final class NativeLib {
                        in.close();
                        out.close();
                        System.load(fileOut.getAbsolutePath());
-
                } catch (Exception e) {
+                       System.err.println("Error while extracting the native library from the jar: ");
+                       e.printStackTrace();
                        throw new SimGridLibNotFoundException("Cannot load the bindings to the "+name+" library in path "+getPath(),   e);
                }
        }
 
        /* A hackish mechanism used to remove the file containing our library when the JVM shuts down */
        private static class FileCleaner implements Runnable {
-               private String target;
-               public FileCleaner(String name) {
-                       target = name;
+               private File dir;
+               public FileCleaner(File dir) {
+                       this.dir = dir;
                }
                public void run() {
                        try {
-                               new File(target).delete();
+                           for (File f : dir.listFiles())
+                               f.delete();
+                               dir.delete();
                        } catch(Exception e) {
-                               System.out.println("Unable to clean temporary file "+target+" during shutdown.");
+                               System.out.println("Unable to clean temporary file "+dir.getAbsolutePath()+" during shutdown.");
                                e.printStackTrace();
                        }
                }    
@@ -118,11 +142,7 @@ public final class NativeLib {
 
 
        public static void main(String[] args) {
-               if (args.length >= 1 && args[0].equals("--quiet"))
-                       /* be careful, this execution path is used in tools/cmake/Scripts/java_bundle.sh to determine where to put the libs */
-                       System.out.println(getPath());
-               else 
-                       System.out.println("This java library will try to load the native code under the following name:\n" +getPath());
+               System.out.println("This jarfile searches the native code under: " +getPath());
        }
 }
 
index b4d2341..86c33cb 100644 (file)
@@ -80,7 +80,7 @@ public class Comm {
         */
        public static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }       
 }
index bd19252..015d080 100644 (file)
@@ -45,12 +45,10 @@ public class File {
         */
        public native void close();
 
-       /**
-        * Class initializer, to initialize various JNI stuff
-        */
+       /** Class initializer, to initialize various JNI stuff */
        public static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }       
 }
\ No newline at end of file
index 8153a42..b324db8 100644 (file)
@@ -11,19 +11,6 @@ import org.simgrid.NativeLib;
 
 
 public final class Msg {
-       /* Statically load the library which contains all native functions used in here */
-       static private boolean isNativeInited = false;
-       public static void nativeInit() {
-               if (isNativeInited)
-                       return;
-               NativeLib.nativeInit("simgrid");
-               NativeLib.nativeInit("simgrid-java");      
-               isNativeInited = true;
-       }
-
-       static {
-               nativeInit();
-       }
 
        /** Retrieve the simulation time
         * @return The simulation time.
@@ -122,4 +109,9 @@ public final class Msg {
                /* Execute the simulation */
                Msg.run();
        }
+       
+       /* Class initializer, to initialize various JNI stuff */
+       static {
+               org.simgrid.NativeLib.nativeInit();
+       }
 }
index 503588b..ed7340b 100644 (file)
@@ -34,7 +34,7 @@ public class Mutex {
         */
        public static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }       
 }
index 5c55f10..5e53e74 100644 (file)
@@ -363,7 +363,7 @@ public abstract class Process implements Runnable {
         */
        private static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }
        /**
index 9e0ec6f..23e95cb 100644 (file)
@@ -113,7 +113,7 @@ public class RngStream {
         */
        public static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }
 }
index 9be79f6..0172aa3 100644 (file)
@@ -80,7 +80,7 @@ public class Semaphore {
         */
        public static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }
 }
\ No newline at end of file
index 46f568a..2b9481f 100644 (file)
@@ -363,7 +363,7 @@ public class Task {
         */
        public static native void nativeInit();
        static {
-               Msg.nativeInit();
+               org.simgrid.NativeLib.nativeInit();
                nativeInit();
        }
 
index aad944c..af1eff3 100644 (file)
@@ -13,8 +13,7 @@ import org.simgrid.NativeLib;
 public class SurfJNI {
 
   static {
-    NativeLib.nativeInit("simgrid");
-    NativeLib.nativeInit("surf-java");
+    org.simgrid.NativeLib.nativeInit();    
     Runtime.getRuntime().addShutdownHook(
       new Thread() {
         public void run() {
index 4892ac3..70cb9e0 100644 (file)
@@ -8,12 +8,12 @@
 
 package org.simgrid.trace;
 
-import org.simgrid.msg.Msg;
+import org.simgrid.NativeLib;
 
 public final class Trace {
        /* Statically load the library which contains all native functions used in here */
        static {
-               Msg.nativeInit();
+               NativeLib.nativeInit();
        }
 
        // TODO complete the binding of the tracing API 
index 29489d1..6d7206d 100644 (file)
@@ -97,7 +97,7 @@ static void* smx_ctx_java_thread_run(void *data) {
   xbt_os_thread_set_extra_data(context);
   //Attach the thread to the JVM
   JNIEnv *env;
-  _XBT_GNUC_UNUSED jint error = (*__java_vm)->AttachCurrentThread(__java_vm, (void **) &env, NULL);
+  XBT_ATTRIB_UNUSED jint error = (*__java_vm)->AttachCurrentThread(__java_vm, (void **) &env, NULL);
   xbt_assert((error == JNI_OK), "The thread could not be attached to the JVM");
   context->jenv = get_current_thread_env();
   //Wait for the first scheduling round to happen.
@@ -168,7 +168,7 @@ void smx_ctx_java_stop(smx_context_t context)
     /* detach the thread and kills it */
     JNIEnv *env = ctx_java->jenv;
     (*env)->DeleteGlobalRef(env,ctx_java->jprocess);
-    _XBT_GNUC_UNUSED jint error = (*__java_vm)->DetachCurrentThread(__java_vm);
+    XBT_ATTRIB_UNUSED jint error = (*__java_vm)->DetachCurrentThread(__java_vm);
     xbt_assert((error == JNI_OK), "The thread couldn't be detached.");
     xbt_os_sem_release(((smx_ctx_java_t)context)->end);
     xbt_os_thread_exit(NULL);
index 7e0c774..95c1130 100644 (file)
@@ -16,8 +16,7 @@ import org.simgrid.NativeLib;
 %}
 %pragma(java) jniclasscode=%{
   static {
-    NativeLib.nativeInit("simgrid");
-    NativeLib.nativeInit("surf-java");
+    org.simgrid.NativeLib.nativeInit();    
     Runtime.getRuntime().addShutdownHook(
       new Thread() {
         public void run() {
index 5128ec5..93d8271 100644 (file)
@@ -465,7 +465,7 @@ static void sglua_copy_function(lua_State* src, lua_State* dst) {
     buffer.data = xbt_new(char, buffer.capacity);
 
     /* copy the binary chunk from src into a buffer */
-    _XBT_GNUC_UNUSED int error = lua_dump(src, sglua_memory_writer, &buffer);
+    XBT_ATTRIB_UNUSED int error = lua_dump(src, sglua_memory_writer, &buffer);
     xbt_assert(!error, "Failed to dump the function from the source state: error %d",
         error);
     XBT_DEBUG("Fonction dumped: %zu bytes", buffer.size);
index 438ba57..f15d691 100644 (file)
@@ -333,7 +333,7 @@ static int run_lua_code(int argc, char **argv)
     lua_pushstring(L, argv[i]);
 
   /* call the function */
-  _XBT_GNUC_UNUSED int err;
+  XBT_ATTRIB_UNUSED int err;
   err = lua_pcall(L, argc - 1, 1, 0);
   xbt_assert(err == 0, "Error running function `%s': %s", argv[0],
               lua_tostring(L, -1));
index b86592b..c33ed9b 100644 (file)
@@ -39,10 +39,6 @@ typedef struct s_stack_region{
   int process_index;
 }s_stack_region_t, *stack_region_t;
 
-void heap_ignore_region_free(mc_heap_ignore_region_t r);
-void heap_ignore_region_free_voidp(void *r);
-
-
 /************ DWARF structures *************/
 
 SG_END_DECL()
index 2f4ec26..2757e7c 100644 (file)
@@ -7,6 +7,7 @@
 #ifndef _MC_MC_H
 #define _MC_MC_H
 
+#include "xbt/base.h"
 #include "xbt/misc.h"
 #include "xbt/fifo.h"
 #include "xbt/dict.h"
 SG_BEGIN_DECL()
 
 /********************************** Configuration of MC **************************************/        
-extern int _sg_do_model_check;
-extern int _sg_do_model_check_record;
-extern int _sg_mc_checkpoint;
-extern int _sg_mc_sparse_checkpoint;
-extern char* _sg_mc_property_file;
-extern int _sg_mc_timeout;
-extern int _sg_mc_hash;
-extern int _sg_mc_max_depth;
-extern int _sg_mc_visited;
-extern char* _sg_mc_dot_output_file;
-extern int _sg_mc_comms_determinism;
-extern int _sg_mc_send_determinism;
-extern int _sg_mc_safety;
-extern int _sg_mc_liveness;
-extern int _sg_mc_snapshot_fds;
-extern int _sg_mc_termination;
+
+extern XBT_PUBLIC(int) _sg_do_model_check;
+extern XBT_PRIVATE int _sg_do_model_check_record;
+extern XBT_PRIVATE int _sg_mc_checkpoint;
+extern XBT_PUBLIC(int) _sg_mc_sparse_checkpoint;
+extern XBT_PUBLIC(int) _sg_mc_ksm;
+extern XBT_PUBLIC(int) _sg_mc_soft_dirty;
+extern XBT_PUBLIC(char*) _sg_mc_property_file;
+extern XBT_PRIVATE int _sg_mc_timeout;
+extern XBT_PRIVATE int _sg_mc_hash;
+extern XBT_PRIVATE int _sg_mc_max_depth;
+extern XBT_PUBLIC(int) _sg_mc_visited;
+extern XBT_PRIVATE char* _sg_mc_dot_output_file;
+extern XBT_PUBLIC(int) _sg_mc_comms_determinism;
+extern XBT_PUBLIC(int) _sg_mc_send_determinism;
+extern XBT_PRIVATE int _sg_mc_safety;
+extern XBT_PRIVATE int _sg_mc_liveness;
+extern XBT_PRIVATE int _sg_mc_snapshot_fds;
+extern XBT_PRIVATE int _sg_mc_termination;
+
+extern XBT_PRIVATE xbt_dynar_t mc_heap_comparison_ignore;
+extern XBT_PRIVATE xbt_dynar_t stacks_areas;
+
+/********************************* Global *************************************/
+
+XBT_PRIVATE void _mc_cfg_cb_reduce(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_checkpoint(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_sparse_checkpoint(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_ksm(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_soft_dirty(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_property(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_timeout(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_snapshot_fds(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_hash(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_max_depth(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_visited(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_dot_output(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_comms_determinism(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_send_determinism(const char *name, int pos);
+XBT_PRIVATE void _mc_cfg_cb_termination(const char *name, int pos);
 
 extern xbt_dynar_t mc_heap_comparison_ignore;
 extern xbt_dynar_t stacks_areas;
@@ -60,6 +85,8 @@ extern xbt_dynar_t stacks_areas;
 void _mc_cfg_cb_reduce(const char *name, int pos);
 void _mc_cfg_cb_checkpoint(const char *name, int pos);
 void _mc_cfg_cb_sparse_checkpoint(const char *name, int pos);
+void _mc_cfg_cb_soft_dirty(const char *name, int pos);
+void _mc_cfg_cb_ksm(const char *name, int pos);
 void _mc_cfg_cb_property(const char *name, int pos);
 void _mc_cfg_cb_timeout(const char *name, int pos);
 void _mc_cfg_cb_hash(const char *name, int pos);
@@ -76,7 +103,7 @@ XBT_PUBLIC(void) MC_init(void);
 XBT_PUBLIC(void) MC_exit(void);
 XBT_PUBLIC(void) MC_process_clock_add(smx_process_t, double);
 XBT_PUBLIC(double) MC_process_clock_get(smx_process_t);
-void MC_automaton_load(const char *file);
+XBT_PRIVATE void MC_automaton_load(const char *file);
 
 /****************************** MC ignore **********************************/
 XBT_PUBLIC(void) MC_ignore_heap(void *address, size_t size);
index 2c1c75a..fbe0d5e 100644 (file)
@@ -23,7 +23,7 @@ XBT_PUBLIC(int) sg_cfg_get_boolean(const char* name);
 XBT_PUBLIC(void) sg_cfg_get_peer(const char *name, char **peer, int *port);
 XBT_PUBLIC(xbt_dynar_t) sg_cfg_get_dynar(const char* name);
 
-void sg_config_init(int *argc, char **argv);
-void sg_config_finalize(void);
+XBT_PUBLIC(void) sg_config_init(int *argc, char **argv);
+XBT_PUBLIC(void) sg_config_finalize(void);
 
 SG_END_DECL()
index 25845ca..7b37c8e 100644 (file)
@@ -119,8 +119,8 @@ XBT_PUBLIC(int) find_coll_description(s_mpi_coll_description_t * table,
                                       char *name, const char *desc);
 
 
-extern double smpi_wtime_sleep;
-extern double smpi_iprobe_sleep;
-extern double smpi_test_sleep;
+extern XBT_PRIVATE double smpi_wtime_sleep;
+extern XBT_PRIVATE double smpi_iprobe_sleep;
+extern XBT_PRIVATE double smpi_test_sleep;
 
 #endif                          /* _SMPI_INTERFAC_H */
index 2239f4a..3394673 100644 (file)
@@ -12,7 +12,6 @@
 #include "xbt/asserts.h"
 #include "surf/datatypes.h"
 #include <math.h>
-//#include <float.h>
 
 
 /** @addtogroup SURF_lmm 
@@ -87,8 +86,8 @@
  * to consrtaint and the communications to variables.
  */
 
-extern double sg_maxmin_precision;
-extern double sg_surf_precision;
+XBT_PUBLIC_DATA(double) sg_maxmin_precision;
+XBT_PUBLIC_DATA(double) sg_surf_precision;
  
 static XBT_INLINE void double_update(double *variable, double value, double precision)
 {
index 31522c6..25468da 100644 (file)
@@ -25,13 +25,13 @@ SG_BEGIN_DECL()
 /* Actions and models are highly connected structures... */
 
 /* user-visible parameters */
-extern double sg_tcp_gamma;
-extern double sg_sender_gap;
-extern double sg_latency_factor;
-extern double sg_bandwidth_factor;
-extern double sg_weight_S_parameter;
-extern int sg_network_crosstraffic;
-extern xbt_dynar_t surf_path;
+extern XBT_PRIVATE double sg_tcp_gamma;
+extern XBT_PRIVATE double sg_sender_gap;
+extern XBT_PRIVATE double sg_latency_factor;
+extern XBT_PRIVATE double sg_bandwidth_factor;
+extern XBT_PRIVATE double sg_weight_S_parameter;
+extern XBT_PRIVATE int sg_network_crosstraffic;
+extern XBT_PRIVATE xbt_dynar_t surf_path;
 
 typedef enum {
   SURF_NETWORK_ELEMENT_NULL = 0,        /* NULL */
index 722dbbc..437782f 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef INSTR_PRIVATE_H_
 #define INSTR_PRIVATE_H_
 
+#include <xbt/base.h>
+
 #include "simgrid/instr.h"
 #include "instr/instr_interface.h"
 #include "internal_config.h"
@@ -224,23 +226,23 @@ typedef struct s_newEvent {
   val_t value;
 }s_newEvent_t;
 
-extern xbt_dict_t created_categories;
-extern xbt_dict_t declared_marks;
-extern xbt_dict_t user_host_variables;
-extern xbt_dict_t user_vm_variables;
-extern xbt_dict_t user_link_variables;
-extern double TRACE_last_timestamp_to_dump;
+extern XBT_PRIVATE xbt_dict_t created_categories;
+extern XBT_PRIVATE xbt_dict_t declared_marks;
+extern XBT_PRIVATE xbt_dict_t user_host_variables;
+extern XBT_PRIVATE xbt_dict_t user_vm_variables;
+extern XBT_PRIVATE xbt_dict_t user_link_variables;
+extern XBT_PRIVATE double TRACE_last_timestamp_to_dump;
 
 /* instr_paje_header.c */
-void TRACE_header(int basic, int size);
+XBT_PRIVATE void TRACE_header(int basic, int size);
 
 /* from paje.c */
-void TRACE_init(void);
-void TRACE_finalize(void);
-void TRACE_paje_init(void);
-void TRACE_paje_start(void);
-void TRACE_paje_end(void);
-void TRACE_paje_dump_buffer (int force);
+XBT_PRIVATE void TRACE_init(void);
+XBT_PRIVATE void TRACE_finalize(void);
+XBT_PRIVATE void TRACE_paje_init(void);
+XBT_PRIVATE void TRACE_paje_start(void);
+XBT_PRIVATE void TRACE_paje_end(void);
+XBT_PRIVATE void TRACE_paje_dump_buffer (int force);
 XBT_PUBLIC(void) new_pajeDefineContainerType(type_t type);
 XBT_PUBLIC(void) new_pajeDefineVariableType(type_t type);
 XBT_PUBLIC(void) new_pajeDefineStateType(type_t type);
@@ -263,32 +265,32 @@ XBT_PUBLIC(void) new_pajeEndLink (double timestamp, container_t container, type_
 XBT_PUBLIC(void) new_pajeNewEvent (double timestamp, container_t container, type_t type, val_t value);
 
 /* from instr_config.c */
-int TRACE_needs_platform (void);
-int TRACE_is_enabled(void);
-int TRACE_platform(void);
-int TRACE_platform_topology(void);
-int TRACE_is_configured(void);
-int TRACE_categorized (void);
-int TRACE_uncategorized (void);
-int TRACE_msg_process_is_enabled(void);
-int TRACE_msg_vm_is_enabled(void);
-int TRACE_buffer (void);
-int TRACE_disable_link(void);
-int TRACE_disable_power(void);
-int TRACE_onelink_only (void);
-int TRACE_disable_destroy (void);
-int TRACE_basic (void);
-int TRACE_display_sizes (void);
-char *TRACE_get_comment (void);
-char *TRACE_get_comment_file (void);
-int TRACE_precision (void);
-char *TRACE_get_filename(void);
-char *TRACE_get_viva_uncat_conf (void);
-char *TRACE_get_viva_cat_conf (void);
-void TRACE_generate_viva_uncat_conf (void);
-void TRACE_generate_viva_cat_conf (void);
-void instr_pause_tracing (void);
-void instr_resume_tracing (void);
+XBT_PRIVATE int TRACE_needs_platform (void);
+XBT_PRIVATE int TRACE_is_enabled(void);
+XBT_PRIVATE int TRACE_platform(void);
+XBT_PRIVATE int TRACE_platform_topology(void);
+XBT_PRIVATE int TRACE_is_configured(void);
+XBT_PRIVATE int TRACE_categorized (void);
+XBT_PRIVATE int TRACE_uncategorized (void);
+XBT_PRIVATE int TRACE_msg_process_is_enabled(void);
+XBT_PRIVATE int TRACE_msg_vm_is_enabled(void);
+XBT_PRIVATE int TRACE_buffer (void);
+XBT_PRIVATE int TRACE_disable_link(void);
+XBT_PRIVATE int TRACE_disable_power(void);
+XBT_PRIVATE int TRACE_onelink_only (void);
+XBT_PRIVATE int TRACE_disable_destroy (void);
+XBT_PRIVATE int TRACE_basic (void);
+XBT_PRIVATE int TRACE_display_sizes (void);
+XBT_PRIVATE char *TRACE_get_comment (void);
+XBT_PRIVATE char *TRACE_get_comment_file (void);
+XBT_PRIVATE int TRACE_precision (void);
+XBT_PRIVATE char *TRACE_get_filename(void);
+XBT_PRIVATE char *TRACE_get_viva_uncat_conf (void);
+XBT_PRIVATE char *TRACE_get_viva_cat_conf (void);
+XBT_PRIVATE void TRACE_generate_viva_uncat_conf (void);
+XBT_PRIVATE void TRACE_generate_viva_cat_conf (void);
+XBT_PRIVATE void instr_pause_tracing (void);
+XBT_PRIVATE void instr_resume_tracing (void);
 
 /* Public functions used in SMPI */
 XBT_PUBLIC(int) TRACE_smpi_is_enabled(void);
@@ -298,12 +300,12 @@ XBT_PUBLIC(int) TRACE_smpi_is_sleeping(void);
 XBT_PUBLIC(int) TRACE_smpi_view_internals(void);
 
 /* from resource_utilization.c */
-void TRACE_surf_host_set_utilization(const char *resource,
+XBT_PRIVATE void TRACE_surf_host_set_utilization(const char *resource,
                                      const char *category,
                                      double value,
                                      double now,
                                      double delta);
-void TRACE_surf_link_set_utilization(const char *resource,
+XBT_PRIVATE void TRACE_surf_link_set_utilization(const char *resource,
                                      const char *category,
                                      double value,
                                      double now,
@@ -311,11 +313,11 @@ void TRACE_surf_link_set_utilization(const char *resource,
 XBT_PUBLIC(void) TRACE_surf_resource_utilization_alloc(void);
 
 /* instr_paje.c */
-extern xbt_dict_t trivaNodeTypes;
-extern xbt_dict_t trivaEdgeTypes;
-long long int instr_new_paje_id (void);
-void PJ_container_alloc (void);
-void PJ_container_release (void);
+extern XBT_PRIVATE xbt_dict_t trivaNodeTypes;
+extern XBT_PRIVATE xbt_dict_t trivaEdgeTypes;
+XBT_PRIVATE long long int instr_new_paje_id (void);
+XBT_PRIVATE void PJ_container_alloc (void);
+XBT_PRIVATE void PJ_container_release (void);
 XBT_PUBLIC(container_t) PJ_container_new (const char *name, e_container_types kind, container_t father);
 XBT_PUBLIC(container_t) PJ_container_get (const char *name);
 XBT_PUBLIC(container_t) PJ_container_get_or_null (const char *name);
@@ -326,55 +328,55 @@ XBT_PUBLIC(void) PJ_container_free_all (void);
 XBT_PUBLIC(void) PJ_container_remove_from_parent (container_t container);
 
 /* instr_paje_types.c */
-void PJ_type_alloc (void);
-void PJ_type_release (void);
+XBT_PRIVATE void PJ_type_alloc (void);
+XBT_PRIVATE void PJ_type_release (void);
 XBT_PUBLIC(type_t)  PJ_type_get_root (void);
-type_t PJ_type_container_new (const char *name, type_t father);
-type_t PJ_type_event_new (const char *name, type_t father);
-type_t PJ_type_variable_new (const char *name, const char *color, type_t father);
+XBT_PRIVATE type_t PJ_type_container_new (const char *name, type_t father);
+XBT_PRIVATE type_t PJ_type_event_new (const char *name, type_t father);
 type_t PJ_type_link_new (const char *name, type_t father, type_t source, type_t dest);
-type_t PJ_type_state_new (const char *name, type_t father);
+XBT_PRIVATE XBT_PRIVATE type_t PJ_type_variable_new (const char *name, const char *color, type_t father);
+XBT_PRIVATE type_t PJ_type_state_new (const char *name, type_t father);
 XBT_PUBLIC(type_t)  PJ_type_get (const char *name, const type_t father);
 XBT_PUBLIC(type_t)  PJ_type_get_or_null (const char *name, type_t father);
-void PJ_type_free (type_t type);
 void PJ_type_free_all (void);
+XBT_PRIVATE XBT_PRIVATE void PJ_type_free (type_t type);
 
 /* instr_paje_values.c */
 XBT_PUBLIC(val_t)  PJ_value_new (const char *name, const char *color, type_t father);
 XBT_PUBLIC(val_t)  PJ_value_get_or_new (const char *name, const char *color, type_t father);
 XBT_PUBLIC(val_t)  PJ_value_get (const char *name, const type_t father);
-void PJ_value_free (val_t value);
-
-void print_pajeDefineContainerType(paje_event_t event);
-void print_pajeDefineVariableType(paje_event_t event);
-void print_pajeDefineStateType(paje_event_t event);
-void print_pajeDefineEventType(paje_event_t event);
-void print_pajeDefineLinkType(paje_event_t event);
-void print_pajeDefineEntityValue (paje_event_t event);
-void print_pajeCreateContainer(paje_event_t event);
-void print_pajeDestroyContainer(paje_event_t event);
-void print_pajeSetVariable(paje_event_t event);
-void print_pajeAddVariable(paje_event_t event);
-void print_pajeSubVariable(paje_event_t event);
-void print_pajeSetState(paje_event_t event);
-void print_pajePushState(paje_event_t event);
-void print_pajePopState(paje_event_t event);
-void print_pajeResetState(paje_event_t event);
-void print_pajeStartLink(paje_event_t event);
-void print_pajeEndLink(paje_event_t event);
-void print_pajeNewEvent (paje_event_t event);
-
-void print_TIPushState(paje_event_t event);
-void print_TICreateContainer(paje_event_t event);
-void print_TIDestroyContainer(paje_event_t event);
-void TRACE_TI_start(void);
-void TRACE_TI_end(void);
-void TRACE_TI_init(void);
-
-void print_NULL (paje_event_t event);
-void TRACE_paje_dump_buffer (int force);
-void dump_comment_file (const char *filename);
-void dump_comment (const char *comment);
+XBT_PRIVATE void PJ_value_free (val_t value);
+
+XBT_PRIVATE void print_pajeDefineContainerType(paje_event_t event);
+XBT_PRIVATE void print_pajeDefineVariableType(paje_event_t event);
+XBT_PRIVATE void print_pajeDefineStateType(paje_event_t event);
+XBT_PRIVATE void print_pajeDefineEventType(paje_event_t event);
+XBT_PRIVATE void print_pajeDefineLinkType(paje_event_t event);
+XBT_PRIVATE void print_pajeDefineEntityValue (paje_event_t event);
+XBT_PRIVATE void print_pajeCreateContainer(paje_event_t event);
+XBT_PRIVATE void print_pajeDestroyContainer(paje_event_t event);
+XBT_PRIVATE void print_pajeSetVariable(paje_event_t event);
+XBT_PRIVATE void print_pajeAddVariable(paje_event_t event);
+XBT_PRIVATE void print_pajeSubVariable(paje_event_t event);
+XBT_PRIVATE void print_pajeSetState(paje_event_t event);
+XBT_PRIVATE void print_pajePushState(paje_event_t event);
+XBT_PRIVATE void print_pajePopState(paje_event_t event);
+XBT_PRIVATE void print_pajeResetState(paje_event_t event);
+XBT_PRIVATE void print_pajeStartLink(paje_event_t event);
+XBT_PRIVATE void print_pajeEndLink(paje_event_t event);
+XBT_PRIVATE void print_pajeNewEvent (paje_event_t event);
+
+XBT_PRIVATE void print_TIPushState(paje_event_t event);
+XBT_PRIVATE void print_TICreateContainer(paje_event_t event);
+XBT_PRIVATE void print_TIDestroyContainer(paje_event_t event);
+XBT_PRIVATE void TRACE_TI_start(void);
+XBT_PRIVATE void TRACE_TI_end(void);
+XBT_PRIVATE void TRACE_TI_init(void);
+
+XBT_PRIVATE void print_NULL (paje_event_t event);
+XBT_PRIVATE void TRACE_paje_dump_buffer (int force);
+XBT_PRIVATE void dump_comment_file (const char *filename);
+XBT_PRIVATE void dump_comment (const char *comment);
 
 
 
index b498665..e23e9ac 100644 (file)
@@ -7,13 +7,12 @@
 #ifndef SIMGRID_MC_ADDRESS_SPACE_H
 #define SIMGRID_MC_ADDRESS_SPACE_H
 
+#include <cstddef>
 #include <cstdint>
 #include <type_traits>
 
 #include <xbt/misc.h>
 
-#include <stdint.h>
-
 #include "mc_forward.hpp"
 
 namespace simgrid {
@@ -128,6 +127,8 @@ const int ProcessIndexDisabled = -2;
 const int ProcessIndexAny = 0;
 
 class AddressSpace {
+private:
+  Process* process_;
 public:
   enum ReadMode {
     Normal,
@@ -136,7 +137,10 @@ public:
      */
     Lazy
   };
+  AddressSpace(Process* process) : process_(process) {}
   virtual ~AddressSpace();
+
+  simgrid::mc::Process* process() { return process_; }
   virtual const void* read_bytes(void* buffer, std::size_t size,
     remote_ptr<void> address, int process_index = ProcessIndexAny,
     ReadMode mode = Normal) const = 0;
index 734b933..64b4848 100644 (file)
@@ -9,6 +9,8 @@
 
 #include <string>
 
+#include <xbt/base.h>
+
 #include "mc_forward.h"
 #include "mc_location.h"
 #include "mc/Variable.hpp"
index 2e41784..f0f65af 100644 (file)
@@ -17,7 +17,8 @@ namespace mc {
 ModelChecker::ModelChecker(pid_t pid, int socket) :
   hostnames_(xbt_dict_new()),
   page_store_(500),
-  process_(pid, socket)
+  process_(pid, socket),
+  parent_snapshot_(nullptr)
 {
 }
 
index 4ce444b..f8b0982 100644 (file)
 
 #include <simgrid_config.h>
 #include <xbt/dict.h>
+#include <xbt/base.h>
 
 #include "mc_forward.hpp"
-#include "mc_process.h"
-#include "PageStore.hpp"
+#include "mc/Process.hpp"
+#include "mc/PageStore.hpp"
 #include "mc_protocol.h"
 
 namespace simgrid {
@@ -34,6 +35,9 @@ class ModelChecker {
   // This is the parent snapshot of the current state:
   PageStore page_store_;
   Process process_;
+public:
+  mc_snapshot_t parent_snapshot_;
+
 public:
   ModelChecker(ModelChecker const&) = delete;
   ModelChecker& operator=(ModelChecker const&) = delete;
@@ -48,6 +52,11 @@ public:
     return page_store_;
   }
   const char* get_host_name(const char* name);
+
+  bool is_important_snapshot(Snapshot const& snapshot) const
+  {
+    return &snapshot == mc_model_checker->parent_snapshot_;
+  }
 };
 
 }
index 8ada283..d589dac 100644 (file)
@@ -11,6 +11,8 @@
 #include <unordered_map>
 #include <vector>
 
+#include <xbt/base.h>
+
 #include "mc/mc_forward.h"
 #include "mc/Type.hpp"
 #include "mc/Frame.hpp"
@@ -88,7 +90,11 @@ public:
 
   bool privatized() const
   {
+#ifdef HAVE_SMPI
     return this->executable() && smpi_privatize_global_variables;
+#else
+    return false;
+#endif
   }
 
   void* base_address() const;
index 5dee482..c3dd009 100644 (file)
@@ -13,6 +13,8 @@
 #include <boost/unordered_map.hpp>
 #include <boost/unordered_set.hpp>
 
+#include <xbt/base.h>
+
 #include "mc_mmu.h"
 #include "mc_forward.hpp"
 
similarity index 87%
rename from src/mc/mc_process.cpp
rename to src/mc/Process.cpp
index c29ebcf..78f4b45 100644 (file)
@@ -27,7 +27,6 @@
 
 #include <xbt/mmalloc.h>
 
-#include "mc_process.h"
 #include "mc_object_info.h"
 #include "mc_unw.h"
 #include "mc_snapshot.h"
@@ -35,6 +34,7 @@
 #include "mc_smx.h"
 #include "mc_server.h"
 
+#include "mc/Process.hpp"
 #include "mc/AddressSpace.hpp"
 #include "mc/ObjectInformation.hpp"
 #include "mc/Variable.hpp"
@@ -54,7 +54,10 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_process, mc,
 static const char *const FILTERED_LIBS[] = {
   "ld",
   "libbz2",
+  "libboost_chrono",
   "libboost_context",
+  "libboost_system",
+  "libboost_thread",
   "libc",
   "libc++",
   "libcdt",
@@ -68,6 +71,7 @@ static const char *const FILTERED_LIBS[] = {
   "libm",
   "libpthread",
   "librt",
+  "libsigc",
   "libstdc++",
   "libunwind",
   "libunwind-x86_64",
@@ -127,6 +131,7 @@ static ssize_t pread_whole(int fd, void *buf, size_t count, std::uint64_t offset
     } else if (res==0) {
       return -1;
     } else if (errno != EINTR) {
+      perror("pread_whole");
       return -1;
     }
   }
@@ -167,6 +172,14 @@ static void MC_zero_buffer_init(void)
   close(fd);
 }
 
+static
+int open_process_file(pid_t pid, const char* file, int flags)
+{
+  char buff[50];
+  snprintf(buff, sizeof(buff), "/proc/%li/%s", (long) pid, file);
+  return open(buff, flags);
+}
+
 }
 
 namespace simgrid {
@@ -193,15 +206,11 @@ int open_vm(pid_t pid, int flags)
 namespace simgrid {
 namespace mc {
 
-Process::Process(pid_t pid, int sockfd)
+Process::Process(pid_t pid, int sockfd) : AddressSpace(this)
 {
   Process* process = this;
-
-  process->process_flags = MC_PROCESS_NO_FLAG;
   process->socket_ = sockfd;
   process->pid_ = pid;
-  if (pid==getpid())
-    process->process_flags |= MC_PROCESS_SELF_FLAG;
   process->running_ = true;
   process->status_ = 0;
   process->memory_map_ = get_memory_map(pid);
@@ -209,16 +218,13 @@ Process::Process(pid_t pid, int sockfd)
   process->heap = NULL;
   process->heap_info = NULL;
   process->init_memory_map_info();
+  process->clear_refs_fd_ = -1;
+  process->pagemap_fd_ = -1;
 
-  // Open the memory file
-  if (process->is_self())
-    process->memory_file = -1;
-  else {
-    int fd = open_vm(process->pid_, O_RDWR);
-    if (fd<0)
-      xbt_die("Could not open file for process virtual address space");
-    process->memory_file = fd;
-  }
+  int fd = open_vm(process->pid_, O_RDWR);
+  if (fd<0)
+    xbt_die("Could not open file for process virtual address space");
+  process->memory_file = fd;
 
   // Read std_heap (is a struct mdesc*):
   simgrid::mc::Variable* std_heap_var = process->find_variable("__mmalloc_default_mdp");
@@ -232,15 +238,9 @@ Process::Process(pid_t pid, int sockfd)
 
   process->smx_process_infos = MC_smx_process_info_list_new();
   process->smx_old_process_infos = MC_smx_process_info_list_new();
-
   process->unw_addr_space = unw_create_addr_space(&mc_unw_accessors  , __BYTE_ORDER);
-  if (process->process_flags & MC_PROCESS_SELF_FLAG) {
-    process->unw_underlying_addr_space = unw_local_addr_space;
-    process->unw_underlying_context = NULL;
-  } else {
-    process->unw_underlying_addr_space = unw_create_addr_space(&mc_unw_vmread_accessors, __BYTE_ORDER);
-    process->unw_underlying_context = _UPT_create(pid);
-  }
+  process->unw_underlying_addr_space = unw_create_addr_space(&mc_unw_vmread_accessors, __BYTE_ORDER);
+  process->unw_underlying_context = _UPT_create(pid);
 }
 
 Process::~Process()
@@ -250,7 +250,6 @@ Process::~Process()
   if (this->socket_ >= 0 && close(this->socket_) < 0)
     xbt_die("Could not close communication socket");
 
-  process->process_flags = MC_PROCESS_NO_FLAG;
   process->pid_ = 0;
 
   process->maestro_stack_start_ = nullptr;
@@ -280,6 +279,11 @@ Process::~Process()
 
   free(process->heap_info);
   process->heap_info = NULL;
+
+  if (process->clear_refs_fd_ >= 0)
+    close(process->clear_refs_fd_);
+  if (process->pagemap_fd_ >= 0)
+    close(process->pagemap_fd_);
 }
 
 /** Refresh the information about the process
@@ -290,7 +294,6 @@ Process::~Process()
 void Process::refresh_heap()
 {
   xbt_assert(mc_mode == MC_MODE_SERVER);
-  xbt_assert(!this->is_self());
   // Read/dereference/refresh the std_heap pointer:
   if (!this->heap) {
     this->heap = (struct mdesc*) malloc(sizeof(struct mdesc));
@@ -308,7 +311,6 @@ void Process::refresh_heap()
 void Process::refresh_malloc_info()
 {
   xbt_assert(mc_mode == MC_MODE_SERVER);
-  xbt_assert(!this->is_self());
   if (!(this->cache_flags & MC_PROCESS_CACHE_FLAG_HEAP))
     this->refresh_heap();
   // Refresh process->heapinfo:
@@ -483,8 +485,6 @@ char* Process::read_string(remote_ptr<void> address) const
 {
   if (!address)
     return NULL;
-  if (this->is_self())
-    return xbt_strdup((char*) address.address());
 
   off_t len = 128;
   char* res = (char*) malloc(len);
@@ -521,6 +521,7 @@ const void *Process::read_bytes(void* buffer, std::size_t size,
     std::shared_ptr<simgrid::mc::ObjectInformation> const& info =
       this->find_object_info_rw((void*)address.address());
     // Segment overlap is not handled.
+#ifdef HAVE_SMPI
     if (info.get() && info.get()->privatized()) {
       if (process_index < 0)
         xbt_die("Missing process index");
@@ -540,20 +541,12 @@ const void *Process::read_bytes(void* buffer, std::size_t size,
       size_t offset = address.address() - (std::uint64_t)info->start_rw;
       address = remote((char*)privatisation_region.address + offset);
     }
+#endif
   }
 
-  if (this->is_self()) {
-    if (mode == simgrid::mc::AddressSpace::Lazy)
-      return (void*)address.address();
-    else {
-      memcpy(buffer, (void*)address.address(), size);
-      return buffer;
-    }
-  } else {
-    if (pread_whole(this->memory_file, buffer, size, address.address()) < 0)
-      xbt_die("Read from process %lli failed", (long long) this->pid_);
-    return buffer;
-  }
+  if (pread_whole(this->memory_file, buffer, size, address.address()) < 0)
+    xbt_die("Read from process %lli failed", (long long) this->pid_);
+  return buffer;
 }
 
 /** Write data to a process memory
@@ -565,26 +558,18 @@ const void *Process::read_bytes(void* buffer, std::size_t size,
  */
 void Process::write_bytes(const void* buffer, size_t len, remote_ptr<void> address)
 {
-  if (this->is_self()) {
-    memcpy((void*)address.address(), buffer, len);
-  } else {
-    if (pwrite_whole(this->memory_file, buffer, len, address.address()) < 0)
-      xbt_die("Write to process %lli failed", (long long) this->pid_);
-  }
+  if (pwrite_whole(this->memory_file, buffer, len, address.address()) < 0)
+    xbt_die("Write to process %lli failed", (long long) this->pid_);
 }
 
 void Process::clear_bytes(remote_ptr<void> address, size_t len)
 {
-  if (this->is_self()) {
-    memset((void*)address.address(), 0, len);
-  } else {
-    pthread_once(&zero_buffer_flag, MC_zero_buffer_init);
-    while (len) {
-      size_t s = len > zero_buffer_size ? zero_buffer_size : len;
-      this->write_bytes(zero_buffer, s, address);
-      address = remote((char*) address.address() + s);
-      len -= s;
-    }
+  pthread_once(&zero_buffer_flag, MC_zero_buffer_init);
+  while (len) {
+    size_t s = len > zero_buffer_size ? zero_buffer_size : len;
+    this->write_bytes(zero_buffer, s, address);
+    address = remote((char*) address.address() + s);
+    len -= s;
   }
 }
 
@@ -636,5 +621,29 @@ void Process::ignore_region(std::uint64_t addr, std::size_t size)
     ignored_regions_.begin() + position, region);
 }
 
+void Process::reset_soft_dirty()
+{
+  if (this->clear_refs_fd_ < 0) {
+    this->clear_refs_fd_ = open_process_file(pid_, "clear_refs", O_WRONLY|O_CLOEXEC);
+    if (this->clear_refs_fd_ < 0)
+      xbt_die("Could not open clear_refs file for soft-dirty tracking. Run as root?");
+  }
+  if(::write(this->clear_refs_fd_, "4\n", 2) != 2)
+    xbt_die("Could not reset softdirty bits");
+}
+
+void Process::read_pagemap(uint64_t* pagemap, size_t page_start, size_t page_count)
+{
+  if (pagemap_fd_ < 0) {
+    pagemap_fd_ = open_process_file(pid_, "pagemap", O_RDONLY|O_CLOEXEC);
+    if (pagemap_fd_ < 0)
+      xbt_die("Could not open pagemap file for soft-dirty tracking. Run as root?");
+  }
+  ssize_t bytesize = sizeof(uint64_t) * page_count;
+  off_t offset = sizeof(uint64_t) * page_start;
+  if (pread_whole(pagemap_fd_, pagemap, bytesize, offset) != bytesize)
+    xbt_die("Could not read pagemap");
+}
+
 }
 }
similarity index 93%
rename from src/mc/mc_process.h
rename to src/mc/Process.hpp
index 100ee17..af42a12 100644 (file)
@@ -17,6 +17,7 @@
 #include "simgrid_config.h"
 #include <sys/types.h>
 
+#include <xbt/base.h>
 #include <xbt/mmalloc.h>
 
 #ifdef HAVE_MC
 #include "AddressSpace.hpp"
 #include "mc_protocol.h"
 
-typedef int mc_process_flags_t;
-#define MC_PROCESS_NO_FLAG 0
-#define MC_PROCESS_SELF_FLAG 1
-
 // Those flags are used to track down which cached information
 // is still up to date and which information needs to be updated.
 typedef int mc_process_cache_flags_t;
@@ -46,8 +43,6 @@ typedef int mc_process_cache_flags_t;
 #define MC_PROCESS_CACHE_FLAG_MALLOC_INFO 2
 #define MC_PROCESS_CACHE_FLAG_SIMIX_PROCESSES 4
 
-typedef struct s_mc_smx_process_info s_mc_smx_process_info_t, *mc_smx_process_info_t;
-
 namespace simgrid {
 namespace mc {
 
@@ -58,16 +53,15 @@ struct IgnoredRegion {
 
 /** Representation of a process
  */
-class Process : public AddressSpace {
+class Process final : public AddressSpace {
 public:
   Process(pid_t pid, int sockfd);
   ~Process();
 
-
-  bool is_self() const
-  {
-    return this->process_flags & MC_PROCESS_SELF_FLAG;
-  }
+  Process(Process const&) = delete;
+  Process(Process &&) = delete;
+  Process& operator=(Process const&) = delete;
+  Process& operator=(Process &&) = delete;
 
   // Read memory:
   const void* read_bytes(void* buffer, std::size_t size,
@@ -157,12 +151,14 @@ public:
     return MC_receive_message(this->socket_, &m, sizeof(M), 0);
   }
 
+  void reset_soft_dirty();
+  void read_pagemap(uint64_t* pagemap, size_t start_page, size_t page_count);
+
 private:
   void init_memory_map_info();
   void refresh_heap();
   void refresh_malloc_info();
 private:
-  mc_process_flags_t process_flags;
   pid_t pid_;
   int socket_;
   int status_;
@@ -171,7 +167,8 @@ private:
   remote_ptr<void> maestro_stack_start_, maestro_stack_end_;
   int memory_file;
   std::vector<IgnoredRegion> ignored_regions_;
-
+  int clear_refs_fd_;
+  int pagemap_fd_;
 public: // object info
   // TODO, make private (first, objectify simgrid::mc::ObjectInformation*)
   std::vector<std::shared_ptr<simgrid::mc::ObjectInformation>> object_infos;
@@ -238,14 +235,14 @@ public: // Libunwind-data
 
 /** Open a FD to a remote process memory (`/dev/$pid/mem`)
  */
-int open_vm(pid_t pid, int flags);
+XBT_PRIVATE int open_vm(pid_t pid, int flags);
 
 }
 }
 
 SG_BEGIN_DECL()
 
-XBT_INTERNAL void MC_invalidate_cache(void);
+XBT_PRIVATE void MC_invalidate_cache(void);
 
 SG_END_DECL()
 
index 4a6e63f..6d50ef1 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <sys/mman.h>
+
 #include "mc/mc.h"
 #include "mc_snapshot.h"
 #include "RegionSnapshot.hpp"
@@ -18,21 +20,62 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_RegionSnaphot, mc,
 namespace simgrid {
 namespace mc {
 
+static inline
+const char* to_cstr(RegionType region)
+{
+  switch (region) {
+  case RegionType::Unknown:
+    return "unknown";
+  case RegionType::Heap:
+    return "Heap";
+  case RegionType::Data:
+    return "Data";
+  default:
+    return "?";
+  }
+}
+
+void data_deleter::operator()(void* p) const
+{
+  switch(type_) {
+  case Free:
+    free(p);
+    break;
+  case Munmap:
+    munmap(p, size_);
+    break;
+  }
+}
+
 RegionSnapshot dense_region(
   RegionType region_type,
   void *start_addr, void* permanent_addr, size_t size)
 {
-  std::vector<char> data(size);
-  mc_model_checker->process().read_bytes(data.data(), size,
+  simgrid::mc::RegionSnapshot::flat_data_ptr data;
+  if (!_sg_mc_ksm)
+    data = simgrid::mc::RegionSnapshot::flat_data_ptr((char*) malloc(size));
+  else {
+    char* ptr = (char*) mmap(nullptr, size, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS|MAP_POPULATE, -1, 0);
+    if (ptr == MAP_FAILED)
+      throw std::bad_alloc();
+    simgrid::mc::data_deleter deleter(
+      simgrid::mc::data_deleter::Munmap, size);
+    data = simgrid::mc::RegionSnapshot::flat_data_ptr(ptr, deleter);
+  }
+  mc_model_checker->process().read_bytes(data.get(), size,
     remote(permanent_addr),
     simgrid::mc::ProcessIndexDisabled);
+  if (_sg_mc_ksm)
+    // Mark the region as mergeable *after* we have written into it.
+    // There no point to let KSM do the hard work before that.
+    madvise(data.get(), size, MADV_MERGEABLE);
 
   simgrid::mc::RegionSnapshot region(
     region_type, start_addr, permanent_addr, size);
   region.flat_data(std::move(data));
 
-  XBT_DEBUG("New region : type : %d, data : %p (real addr %p), size : %zu",
-            region_type, region.flat_data().data(), permanent_addr, size);
+  XBT_DEBUG("New region : type : %s, data : %p (real addr %p), size : %zu",
+            to_cstr(region_type), region.flat_data(), permanent_addr, size);
   return std::move(region);
 }
 
@@ -44,28 +87,45 @@ RegionSnapshot dense_region(
  * @param size         Size of the data*
  */
 RegionSnapshot region(
-  RegionType type, void *start_addr, void* permanent_addr, size_t size)
+  RegionType type, void *start_addr, void* permanent_addr, size_t size,
+  RegionSnapshot const* ref_region)
 {
   if (_sg_mc_sparse_checkpoint) {
-    return sparse_region(type, start_addr, permanent_addr, size);
+    return sparse_region(type, start_addr, permanent_addr, size, ref_region);
   } else  {
     return dense_region(type, start_addr, permanent_addr, size);
   }
 }
 
 RegionSnapshot sparse_region(RegionType region_type,
-  void *start_addr, void* permanent_addr, size_t size)
+  void *start_addr, void* permanent_addr, size_t size,
+  RegionSnapshot const* ref_region)
 {
   simgrid::mc::Process* process = &mc_model_checker->process();
 
+  bool use_soft_dirty = _sg_mc_sparse_checkpoint && _sg_mc_soft_dirty
+    && ref_region != nullptr
+    && ref_region->storage_type() == simgrid::mc::StorageType::Chunked;
+
   xbt_assert((((uintptr_t)start_addr) & (xbt_pagesize-1)) == 0,
     "Not at the beginning of a page");
   xbt_assert((((uintptr_t)permanent_addr) & (xbt_pagesize-1)) == 0,
     "Not at the beginning of a page");
   size_t page_count = mc_page_count(size);
 
-  simgrid::mc::PerPageCopy page_data(mc_model_checker->page_store(), *process,
-      permanent_addr, page_count);
+  std::vector<std::uint64_t> pagemap;
+  const size_t* ref_page_numbers = nullptr;
+  if (use_soft_dirty) {
+    pagemap.resize(page_count);
+    process->read_pagemap(pagemap.data(),
+      mc_page_number(nullptr, permanent_addr), page_count);
+    ref_page_numbers = ref_region->page_data().pagenos();
+  }
+
+  simgrid::mc::PerPageCopy page_data(
+    mc_model_checker->page_store(), *process, permanent_addr, page_count,
+    ref_page_numbers,
+    use_soft_dirty ? pagemap.data() : nullptr);
 
   simgrid::mc::RegionSnapshot region(
     region_type, start_addr, permanent_addr, size);
index 9915186..e54516a 100644 (file)
@@ -10,6 +10,8 @@
 #include <cstddef>
 #include <utility>
 
+#include <xbt/base.h>
+
 #include "PageStore.hpp"
 #include "AddressSpace.hpp"
 
@@ -74,13 +76,17 @@ public:
     return pagenos_[i];
   }
 
+  const std::size_t* pagenos() const { return pagenos_.data(); }
+  std::size_t*       pagenos()       { return pagenos_.data(); }
+
   const void* page(std::size_t i) const
   {
     return store_->get_page(pagenos_[i]);
   }
 
   PerPageCopy(PageStore& store, AddressSpace& as,
-    remote_ptr<void> addr, std::size_t page_count);
+    remote_ptr<void> addr, std::size_t page_count,
+    const size_t* ref_page_numbers, const std::uint64_t* pagemap);
 };
 
 enum class RegionType {
@@ -97,6 +103,21 @@ enum class StorageType {
   Privatized = 3
 };
 
+class data_deleter {
+public:
+  enum Type {
+    Free,
+    Munmap
+  };
+private:
+  Type type_;
+  std::size_t size_;
+public:
+  data_deleter() : type_(Free) {}
+  data_deleter(Type type, std::size_t size) : type_(type), size_(size) {}
+  void operator()(void* p) const;
+};
+
 /** @brief Copy/snapshot of a given memory region
  *
  *  Different types of region snapshot storage types exist:
@@ -114,6 +135,7 @@ enum class StorageType {
  *      each type.
  */
 class RegionSnapshot {
+public:
   static const RegionType UnknownRegion = RegionType::Unknown;
   static const RegionType HeapRegion = RegionType::Heap;
   static const RegionType DataRegion = RegionType::Data;
@@ -121,6 +143,8 @@ class RegionSnapshot {
   static const StorageType FlatData = StorageType::Flat;
   static const StorageType ChunkedData = StorageType::Chunked;
   static const StorageType PrivatizedData = StorageType::Privatized;
+public:
+  typedef std::unique_ptr<char[], data_deleter> flat_data_ptr;
 private:
   RegionType region_type_;
   StorageType storage_type_;
@@ -143,7 +167,7 @@ private:
    * */
   void *permanent_addr_;
 
-  std::vector<char> flat_data_;
+  flat_data_ptr flat_data_;
   PerPageCopy page_numbers_;
   std::vector<RegionSnapshot> privatized_regions_;
 public:
@@ -202,7 +226,7 @@ public:
     storage_type_ = NoData;
     privatized_regions_.clear();
     page_numbers_.clear();
-    flat_data_.clear();
+    flat_data_.reset();
     object_info_ = nullptr;
     start_addr_ = nullptr;
     size_ = 0;
@@ -212,24 +236,24 @@ public:
   void clear_data()
   {
     storage_type_ = NoData;
-    flat_data_.clear();
+    flat_data_.reset();
     page_numbers_.clear();
     privatized_regions_.clear();
   }
   
-  void flat_data(std::vector<char> data)
+  void flat_data(flat_data_ptr data)
   {
     storage_type_ = FlatData;
     flat_data_ = std::move(data);
     page_numbers_.clear();
     privatized_regions_.clear();
   }
-  std::vector<char> const& flat_data() const { return flat_data_; }
+  const char* flat_data() const { return flat_data_.get(); }
 
   void page_data(PerPageCopy page_data)
   {
     storage_type_ = ChunkedData;
-    flat_data_.clear();
+    flat_data_.reset();
     page_numbers_ = std::move(page_data);
     privatized_regions_.clear();
   }
@@ -238,7 +262,7 @@ public:
   void privatized_data(std::vector<RegionSnapshot> data)
   {
     storage_type_ = PrivatizedData;
-    flat_data_.clear();
+    flat_data_.reset();
     page_numbers_.clear();
     privatized_regions_ = std::move(data);
   }
@@ -274,10 +298,12 @@ RegionSnapshot privatized_region(
 RegionSnapshot dense_region(
   RegionType type, void *start_addr, void* data_addr, size_t size);
 simgrid::mc::RegionSnapshot sparse_region(
-  RegionType type, void *start_addr, void* data_addr, size_t size);
+  RegionType type, void *start_addr, void* data_addr, size_t size,
+  RegionSnapshot const* ref_region);
 simgrid::mc::RegionSnapshot region(
-  RegionType type, void *start_addr, void* data_addr, size_t size);
-  
+  RegionType type, void *start_addr, void* data_addr, size_t size,
+  RegionSnapshot const* ref_region);
+
 }
 }
 
index 46a0516..540bf4c 100644 (file)
 #include <vector>
 #include <string>
 
+#include <xbt/base.h>
+
 #include "mc_forward.h"
 #include "mc_location.h"
 
 namespace simgrid {
 namespace mc {
 
-/** Represents a type in the program
- *
- *  It is currently used to represent members of structs and unions as well.
- */
-class Type {
+/** Represent a member of  a structure (or inheritance) */
+class Member {
 public:
-  Type();
-  Type(Type const& type) = default;
-  Type& operator=(Type const&) = default;
-  Type(Type&& type) = default;
-  Type& operator=(Type&&) = default;
-
-  /** The DWARF TAG of the type (e.g. DW_TAG_array_type) */
-  int type;
-  unsigned id; /* Offset in the section (in hexadecimal form) */
-  std::string name; /* Name of the type */
-  int byte_size; /* Size in bytes */
-  int element_count; /* Number of elements for array type */
-  unsigned type_id; /* DW_AT_type id */
-  std::vector<Type> members; /* if DW_TAG_structure_type, DW_TAG_class_type, DW_TAG_union_type*/
-  int is_pointer_type;
+  Member() : inheritance(false), byte_size(0), type_id(0) {}
 
-  // Location (for members) is either of:
+  bool inheritance;
+  std::string name;
   simgrid::mc::DwarfExpression location_expression;
-
-  simgrid::mc::Type* subtype; // DW_AT_type
-  simgrid::mc::Type* full_type; // The same (but more complete) type
+  std::size_t byte_size; // Do we really need this?
+  unsigned type_id;
+  simgrid::mc::Type* type;
 
   bool has_offset_location() const
   {
@@ -66,6 +52,32 @@ public:
   }
 };
 
+/** Represents a type in the program
+ *
+ *  It is currently used to represent members of structs and unions as well.
+ */
+class Type {
+public:
+  Type();
+  Type(Type const& type) = default;
+  Type& operator=(Type const&) = default;
+  Type(Type&& type) = default;
+  Type& operator=(Type&&) = default;
+
+  /** The DWARF TAG of the type (e.g. DW_TAG_array_type) */
+  int type;
+  unsigned id; /* Offset in the section (in hexadecimal form) */
+  std::string name; /* Name of the type */
+  int byte_size; /* Size in bytes */
+  int element_count; /* Number of elements for array type */
+  unsigned type_id; /* DW_AT_type id */
+  std::vector<Member> members; /* if DW_TAG_structure_type, DW_TAG_class_type, DW_TAG_union_type*/
+  int is_pointer_type;
+
+  simgrid::mc::Type* subtype; // DW_AT_type
+  simgrid::mc::Type* full_type; // The same (but more complete) type
+};
+
 inline
 Type::Type()
 {
index 8bae0c7..31f49c9 100644 (file)
@@ -9,6 +9,8 @@
 
 #include <string>
 
+#include <xbt/base.h>
+
 #include "mc_forward.h"
 #include "mc_location.h"
 
index 8c8610f..f38cf7b 100644 (file)
@@ -16,8 +16,8 @@
 #include "mc_protocol.h"
 
 #ifdef HAVE_MC
-#include "mc_process.h"
-#include "ModelChecker.hpp"
+#include "mc/Process.hpp"
+#include "mc/ModelChecker.hpp"
 #include "mc_smx.h"
 #include "mc_server.h"
 #endif
@@ -142,6 +142,9 @@ int MC_request_is_enabled(smx_simcall_t req)
     return FALSE;
   }
 
+  case SIMCALL_MUTEX_TRYLOCK:
+    return TRUE;
+
   case SIMCALL_MUTEX_LOCK: {
     smx_mutex_t mutex = simcall_mutex_lock__get__mutex(req);
 #ifdef HAVE_MC
@@ -179,6 +182,7 @@ int MC_request_is_visible(smx_simcall_t req)
       || req->call == SIMCALL_COMM_TESTANY
       || req->call == SIMCALL_MC_RANDOM
       || req->call == SIMCALL_MUTEX_LOCK
+      || req->call == SIMCALL_MUTEX_TRYLOCK
 #ifdef HAVE_MC
       || req->call == SIMCALL_MC_SNAPSHOT
       || req->call == SIMCALL_MC_COMPARE_SNAPSHOTS
index a72fbce..7b668d5 100644 (file)
 #include "internal_config.h"
 #include "../simix/smx_private.h"
 
-// Marker for symbols which should be defined as XBT_PRIVATE but are used in
-// unit tests:
-#define MC_SHOULD_BE_INTERNAL
-
 SG_BEGIN_DECL()
 
 /** Check if the given simcall can be resolved
  *
  *  \return `TRUE` or `FALSE`
  */
-int MC_request_is_enabled(smx_simcall_t req);
+XBT_PRIVATE int MC_request_is_enabled(smx_simcall_t req);
 
 /** Check if the given simcall is visible
  *
  *  \return `TRUE` or `FALSE`
  */
-int MC_request_is_visible(smx_simcall_t req);
+XBT_PRIVATE int MC_request_is_visible(smx_simcall_t req);
 
 /** Execute everything which is invisible
  *
@@ -37,9 +33,9 @@ int MC_request_is_visible(smx_simcall_t req);
  *  iteratively until there doesn't remain any. At this point, the function
  *  returns to the caller which can handle the visible (and ready) simcalls.
  */
-void MC_wait_for_requests(void);
+XBT_PRIVATE void MC_wait_for_requests(void);
 
-XBT_INTERNAL extern double *mc_time;
+XBT_PRIVATE extern double *mc_time;
 
 SG_END_DECL()
 
index 7f4a821..763e116 100644 (file)
@@ -63,7 +63,7 @@ static void MC_region_restore(mc_mem_region_t region)
     break;
 
   case simgrid::mc::StorageType::Flat:
-    mc_model_checker->process().write_bytes(region->flat_data().data(),
+    mc_model_checker->process().write_bytes(region->flat_data(),
       region->size(), region->permanent_address());
     break;
 
@@ -83,8 +83,10 @@ static void MC_region_restore(mc_mem_region_t region)
 namespace simgrid {
 namespace mc {
 
+#ifdef HAVE_SMPI
 simgrid::mc::RegionSnapshot privatized_region(
-    RegionType region_type, void *start_addr, void* permanent_addr, size_t size
+    RegionType region_type, void *start_addr, void* permanent_addr, size_t size,
+    const simgrid::mc::RegionSnapshot* ref_region
     )
 {
   size_t process_count = MC_smpi_process_count();
@@ -101,17 +103,20 @@ simgrid::mc::RegionSnapshot privatized_region(
 
   std::vector<simgrid::mc::RegionSnapshot> data;
   data.reserve(process_count);
-  for (size_t i = 0; i < process_count; i++)
-    data.push_back(
-      simgrid::mc::region(region_type, start_addr,
-        privatisation_regions[i].address, size)
-      );
+  for (size_t i = 0; i < process_count; i++) {
+    const simgrid::mc::RegionSnapshot* ref_privatized_region = nullptr;
+    if (ref_region && ref_region->storage_type() == StorageType::Privatized)
+      ref_privatized_region = &ref_region->privatized_data()[i];
+    data.push_back(simgrid::mc::region(region_type, start_addr,
+      privatisation_regions[i].address, size, ref_privatized_region));
+  }
 
   simgrid::mc::RegionSnapshot region = simgrid::mc::RegionSnapshot(
     region_type, start_addr, permanent_addr, size);
   region.privatized_data(std::move(data));
   return std::move(region);
 }
+#endif
 
 }
 }
@@ -128,13 +133,19 @@ static void MC_snapshot_add_region(int index, mc_snapshot_t snapshot,
   else if (type == simgrid::mc::RegionType::Heap)
     xbt_assert(!object_info, "Unexpected object info for heap region.");
 
-  const bool privatization_aware = object_info && object_info->privatized();
+  simgrid::mc::RegionSnapshot const* ref_region = nullptr;
+  if (mc_model_checker->parent_snapshot_)
+    ref_region = mc_model_checker->parent_snapshot_->snapshot_regions[index].get();
 
   simgrid::mc::RegionSnapshot region;
+#ifdef HAVE_SMPI
+  const bool privatization_aware = object_info && object_info->privatized();
   if (privatization_aware && MC_smpi_process_count())
-    region = simgrid::mc::privatized_region(type, start_addr, permanent_addr, size);
+    region = simgrid::mc::privatized_region(
+      type, start_addr, permanent_addr, size, ref_region);
   else
-    region = simgrid::mc::region(type, start_addr, permanent_addr, size);
+#endif
+    region = simgrid::mc::region(type, start_addr, permanent_addr, size, ref_region);
 
   region.object_info(object_info);
   snapshot->snapshot_regions[index]
@@ -187,7 +198,7 @@ static void MC_get_memory_regions(simgrid::mc::Process* process, mc_snapshot_t s
 void MC_find_object_address(
   std::vector<simgrid::mc::VmMap> const& maps, simgrid::mc::ObjectInformation* result)
 {
-  const char* file_name = xbt_strdup(result->file_name.c_str());
+  char* file_name = xbt_strdup(result->file_name.c_str());
   const char *name = basename(file_name);
   for (size_t i = 0; i < maps.size(); ++i) {
     simgrid::mc::VmMap const& reg = maps[i];
@@ -235,6 +246,7 @@ void MC_find_object_address(
 
   xbt_assert(result->start_rw);
   xbt_assert(result->start_exec);
+  free(file_name);
 }
 
 /************************************* Take Snapshot ************************************/
@@ -463,7 +475,7 @@ static std::vector<s_mc_heap_ignore_region_t> MC_take_snapshot_ignore()
 
 static void MC_snapshot_handle_ignore(mc_snapshot_t snapshot)
 {
-  xbt_assert(snapshot->process);
+  xbt_assert(snapshot->process());
   
   // Copy the memory:
   for (auto const& region : mc_model_checker->process().ignored_regions()) {
@@ -471,7 +483,7 @@ static void MC_snapshot_handle_ignore(mc_snapshot_t snapshot)
     ignored_data.start = (void*)region.addr;
     ignored_data.data.resize(region.size);
     // TODO, we should do this once per privatization segment:
-    snapshot->process->read_bytes(
+    snapshot->process()->read_bytes(
       ignored_data.data.data(), region.size, remote(region.addr),
       simgrid::mc::ProcessIndexDisabled);
     snapshot->ignored_data.push_back(std::move(ignored_data));
@@ -479,7 +491,7 @@ static void MC_snapshot_handle_ignore(mc_snapshot_t snapshot)
 
   // Zero the memory:
   for(auto const& region : mc_model_checker->process().ignored_regions()) {
-    snapshot->process->clear_bytes(remote(region.addr), region.size);
+    snapshot->process()->clear_bytes(remote(region.addr), region.size);
   }
 
 }
@@ -487,7 +499,7 @@ static void MC_snapshot_handle_ignore(mc_snapshot_t snapshot)
 static void MC_snapshot_ignore_restore(mc_snapshot_t snapshot)
 {
   for (auto const& ignored_data : snapshot->ignored_data)
-    snapshot->process->write_bytes(
+    snapshot->process()->write_bytes(
       ignored_data.data.data(), ignored_data.data.size(),
       remote(ignored_data.start));
 }
@@ -535,8 +547,10 @@ static std::vector<s_fd_infos_t> MC_get_current_fds(pid_t pid)
     }
     link[res] = '\0';
 
+#ifdef HAVE_SMPI
     if(smpi_is_privatisation_file(link))
       continue;
+#endif
 
     // This is (probably) the DIR* we are reading:
     // TODO, read all the file entries at once and close the DIR.*
@@ -575,9 +589,8 @@ mc_snapshot_t MC_take_snapshot(int num_state)
 
   simgrid::mc::Process* mc_process = &mc_model_checker->process();
 
-  mc_snapshot_t snapshot = new simgrid::mc::Snapshot();
+  mc_snapshot_t snapshot = new simgrid::mc::Snapshot(mc_process);
 
-  snapshot->process = mc_process;
   snapshot->num_state = num_state;
 
   smx_process_t process;
@@ -589,15 +602,19 @@ mc_snapshot_t MC_take_snapshot(int num_state)
   if (_sg_mc_snapshot_fds)
     snapshot->current_fds = MC_get_current_fds(process->pid);
 
+  const bool use_soft_dirty = _sg_mc_sparse_checkpoint && _sg_mc_soft_dirty;
+
   /* Save the std heap and the writable mapped pages of libsimgrid and binary */
   MC_get_memory_regions(mc_process, snapshot);
+  if (use_soft_dirty)
+    mc_process->reset_soft_dirty();
 
   snapshot->to_ignore = MC_take_snapshot_ignore();
 
   if (_sg_mc_visited > 0 || strcmp(_sg_mc_property_file, "")) {
     snapshot->stacks =
         MC_take_snapshot_stacks(&snapshot);
-    if (_sg_mc_hash && !snapshot->stacks.empty()) {
+    if (_sg_mc_hash) {
       snapshot->hash = simgrid::mc::hash(*snapshot);
     } else {
       snapshot->hash = 0;
@@ -607,6 +624,8 @@ mc_snapshot_t MC_take_snapshot(int num_state)
   }
 
   MC_snapshot_ignore_restore(snapshot);
+  if (use_soft_dirty)
+    mc_model_checker->parent_snapshot_ = snapshot;
   return snapshot;
 }
 
@@ -657,11 +676,16 @@ void MC_restore_snapshot_fds(mc_snapshot_t snapshot)
 void MC_restore_snapshot(mc_snapshot_t snapshot)
 {
   XBT_DEBUG("Restore snapshot %i", snapshot->num_state);
+  const bool use_soft_dirty = _sg_mc_sparse_checkpoint && _sg_mc_soft_dirty;
   MC_restore_snapshot_regions(snapshot);
   if (_sg_mc_snapshot_fds)
     MC_restore_snapshot_fds(snapshot);
+  if (use_soft_dirty)
+    mc_model_checker->process().reset_soft_dirty();
   MC_snapshot_ignore_restore(snapshot);
   mc_model_checker->process().cache_flags = 0;
+  if (use_soft_dirty)
+    mc_model_checker->parent_snapshot_ = snapshot;
 }
 
 mc_snapshot_t simcall_HANDLER_mc_snapshot(smx_simcall_t simcall)
index 6109240..5ed0cf3 100644 (file)
@@ -4,9 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include <stdlib.h>
-#include <errno.h>
-#include <error.h>
+#include <cstdlib>
+#include <cerrno>
 
 #include <sys/types.h>
 #include <sys/socket.h>
@@ -37,7 +36,7 @@ void MC_client_init(void)
     return;
   }
 
-  char* fd_env = getenv(MC_ENV_SOCKET_FD);
+  char* fd_env = std::getenv(MC_ENV_SOCKET_FD);
   if (!fd_env)
     xbt_die("MC socket not found");
 
index 589e625..515abb7 100644 (file)
@@ -17,13 +17,13 @@ typedef struct s_mc_client {
   int fd;
 } s_mc_client_t, *mc_client_t;
 
-extern XBT_INTERNAL mc_client_t mc_client;
+extern XBT_PRIVATE mc_client_t mc_client;
 
-XBT_INTERNAL void MC_client_init(void);
-XBT_INTERNAL void MC_client_hello(void);
-XBT_INTERNAL void MC_client_handle_messages(void);
-XBT_INTERNAL void MC_client_send_message(void* message, size_t size);
-XBT_INTERNAL void MC_client_send_simple_message(e_mc_message_type type);
+XBT_PRIVATE void MC_client_init(void);
+XBT_PRIVATE void MC_client_hello(void);
+XBT_PRIVATE void MC_client_handle_messages(void);
+XBT_PRIVATE void MC_client_send_message(void* message, size_t size);
+XBT_PRIVATE void MC_client_send_simple_message(e_mc_message_type type);
 
 #ifdef HAVE_MC
 void MC_ignore(void* addr, size_t size);
index 2121e9f..5b2215b 100644 (file)
@@ -7,7 +7,7 @@
 #ifndef SIMGRID_MC_COMM_PATTERN_H
 #define SIMGRID_MC_COMM_PATTERN_H
 
-#include <stdint.h>
+#include <stddef.h>
 
 #include <simgrid_config.h>
 #include <xbt/dynar.h>
@@ -43,12 +43,12 @@ typedef struct s_mc_list_comm_pattern{
 /**
  *  Type: `xbt_dynar_t<mc_list_comm_pattenr_t>`
  */
-extern XBT_INTERNAL xbt_dynar_t initial_communications_pattern;
+extern XBT_PRIVATE xbt_dynar_t initial_communications_pattern;
 
 /**
  *  Type: `xbt_dynar_t<xbt_dynar_t<mc_comm_pattern_t>>`
  */
-extern XBT_INTERNAL xbt_dynar_t incomplete_communications_pattern;
+extern XBT_PRIVATE xbt_dynar_t incomplete_communications_pattern;
 
 typedef enum {
   MC_CALL_TYPE_NONE,
@@ -85,22 +85,22 @@ static inline e_mc_call_type_t MC_get_call_type(smx_simcall_t req)
   }
 }
 
-XBT_INTERNAL void MC_get_comm_pattern(xbt_dynar_t communications_pattern, smx_simcall_t request, e_mc_call_type_t call_type, int backtracking);
-XBT_INTERNAL void MC_handle_comm_pattern(e_mc_call_type_t call_type, smx_simcall_t request, int value, xbt_dynar_t current_pattern, int backtracking);
-XBT_INTERNAL void MC_comm_pattern_free_voidp(void *p);
-XBT_INTERNAL void MC_list_comm_pattern_free_voidp(void *p);
-XBT_INTERNAL void MC_complete_comm_pattern(xbt_dynar_t list, smx_synchro_t comm_addr, unsigned int issuer, int backtracking);
+XBT_PRIVATE void MC_get_comm_pattern(xbt_dynar_t communications_pattern, smx_simcall_t request, e_mc_call_type_t call_type, int backtracking);
+XBT_PRIVATE void MC_handle_comm_pattern(e_mc_call_type_t call_type, smx_simcall_t request, int value, xbt_dynar_t current_pattern, int backtracking);
+XBT_PRIVATE void MC_comm_pattern_free_voidp(void *p);
+XBT_PRIVATE void MC_list_comm_pattern_free_voidp(void *p);
+XBT_PRIVATE void MC_complete_comm_pattern(xbt_dynar_t list, smx_synchro_t comm_addr, unsigned int issuer, int backtracking);
 void MC_modelcheck_comm_determinism(void);
 
-XBT_INTERNAL void MC_restore_communications_pattern(mc_state_t state);
+XBT_PRIVATE void MC_restore_communications_pattern(mc_state_t state);
 
-XBT_INTERNAL mc_comm_pattern_t MC_comm_pattern_dup(mc_comm_pattern_t comm);
-XBT_INTERNAL xbt_dynar_t MC_comm_patterns_dup(xbt_dynar_t state);
+XBT_PRIVATE mc_comm_pattern_t MC_comm_pattern_dup(mc_comm_pattern_t comm);
+XBT_PRIVATE xbt_dynar_t MC_comm_patterns_dup(xbt_dynar_t state);
 
-XBT_INTERNAL void MC_state_copy_incomplete_communications_pattern(mc_state_t state);
-XBT_INTERNAL void MC_state_copy_index_communications_pattern(mc_state_t state);
+XBT_PRIVATE void MC_state_copy_incomplete_communications_pattern(mc_state_t state);
+XBT_PRIVATE void MC_state_copy_index_communications_pattern(mc_state_t state);
 
-XBT_INTERNAL void MC_comm_pattern_free(mc_comm_pattern_t p);
+XBT_PRIVATE void MC_comm_pattern_free(mc_comm_pattern_t p);
 
 SG_END_DECL()
 
index 2d04cb8..49ca977 100644 (file)
@@ -16,6 +16,7 @@
 #include "mc_liveness.h"
 #include "mc_private.h"
 #include "mc_smx.h"
+#include "mc_dwarf.hpp"
 
 #include "mc/Frame.hpp"
 #include "mc/ObjectInformation.hpp"
@@ -236,7 +237,7 @@ static int compare_areas_with_type(struct mc_compare_state& state,
   }
   case DW_TAG_structure_type:
   case DW_TAG_class_type:
-    for(simgrid::mc::Type& member : type->members) {
+    for(simgrid::mc::Member& member : type->members) {
       void *member1 =
         mc_member_resolve(real_area1, type, &member, snapshot1, process_index);
       void *member2 =
@@ -247,7 +248,7 @@ static int compare_areas_with_type(struct mc_compare_state& state,
           compare_areas_with_type(state, process_index,
                                   member1, snapshot1, subregion1,
                                   member2, snapshot2, subregion2,
-                                  member.subtype, pointer_level);
+                                  member.type, pointer_level);
       if (res == 1)
         return res;
     }
index 4c6960a..147b38a 100644 (file)
@@ -4,8 +4,7 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include <strings.h>
-
+#include <xbt/str.h>
 #include <xbt/log.h>
 #include <xbt/config.h>
 
@@ -41,7 +40,7 @@ void _mc_cfg_cb_timeout(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !(_sg_do_model_check || MC_record_path)) {
     xbt_die
-        ("You are specifying a value to enable/disable timeout for wait requests after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a value to enable/disable timeout for wait requests after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_timeout = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
@@ -51,6 +50,8 @@ int _sg_do_model_check = 0;
 int _sg_do_model_check_record = 0;
 int _sg_mc_checkpoint = 0;
 int _sg_mc_sparse_checkpoint = 0;
+int _sg_mc_soft_dirty = 0;
+int _sg_mc_ksm = 0;
 char *_sg_mc_property_file = NULL;
 int _sg_mc_hash = 0;
 int _sg_mc_max_depth = 1000;
@@ -67,7 +68,7 @@ void _mc_cfg_cb_reduce(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a reduction strategy after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a reduction strategy after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   char *val = xbt_cfg_get_string(_sg_cfg_set, name);
   if (!strcasecmp(val, "none")) {
@@ -84,23 +85,39 @@ void _mc_cfg_cb_checkpoint(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a checkpointing value after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a checkpointing value after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_checkpoint = xbt_cfg_get_int(_sg_cfg_set, name);
 }
 
 void _mc_cfg_cb_sparse_checkpoint(const char *name, int pos) {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
-    xbt_die("You are specifying a checkpointing value after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+    xbt_die("You are specifying a checkpointing value after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_sparse_checkpoint = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
 
+void _mc_cfg_cb_soft_dirty(const char *name, int pos) {
+  if (_sg_cfg_init_status && !_sg_do_model_check)
+    xbt_die("You are specifying a soft dirty value after the initialization "
+            "(through MSG_config?), but model-checking was not activated "
+            "at config time (through --cfg=model-check:1). "
+            "This won't work, sorry.");
+  _sg_mc_soft_dirty = xbt_cfg_get_boolean(_sg_cfg_set, name);
+}
+
+void _mc_cfg_cb_ksm(const char *name, int pos)
+{
+  if (_sg_cfg_init_status && !_sg_do_model_check)
+    xbt_die("You are specifying a KSM value after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+  _sg_mc_ksm = xbt_cfg_get_boolean(_sg_cfg_set, name);
+}
+
 void _mc_cfg_cb_property(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a property after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a property after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_property_file = xbt_cfg_get_string(_sg_cfg_set, name);
 }
@@ -109,7 +126,7 @@ void _mc_cfg_cb_hash(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a value to enable/disable the use of global hash to speedup state comparaison, but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a value to enable/disable the use of global hash to speedup state comparaison, but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_hash = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
@@ -118,7 +135,7 @@ void _mc_cfg_cb_snapshot_fds(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a value to enable/disable the use of FD snapshoting, but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a value to enable/disable the use of FD snapshoting, but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_snapshot_fds = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
@@ -127,7 +144,7 @@ void _mc_cfg_cb_max_depth(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a max depth value after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a max depth value after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_max_depth = xbt_cfg_get_int(_sg_cfg_set, name);
 }
@@ -136,7 +153,7 @@ void _mc_cfg_cb_visited(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a number of stored visited states after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a number of stored visited states after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_visited = xbt_cfg_get_int(_sg_cfg_set, name);
 }
@@ -145,7 +162,7 @@ void _mc_cfg_cb_dot_output(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a file name for a dot output of graph state after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a file name for a dot output of graph state after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_dot_output_file = xbt_cfg_get_string(_sg_cfg_set, name);
 }
@@ -154,7 +171,7 @@ void _mc_cfg_cb_comms_determinism(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a value to enable/disable the detection of determinism in the communications schemes after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a value to enable/disable the detection of determinism in the communications schemes after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_comms_determinism = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
@@ -163,7 +180,7 @@ void _mc_cfg_cb_send_determinism(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a value to enable/disable the detection of send-determinism in the communications schemes after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a value to enable/disable the detection of send-determinism in the communications schemes after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_send_determinism = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
@@ -172,7 +189,7 @@ void _mc_cfg_cb_termination(const char *name, int pos)
 {
   if (_sg_cfg_init_status && !_sg_do_model_check) {
     xbt_die
-        ("You are specifying a value to enable/disable the detection of non progressive cycles after the initialization (through MSG_config?), but model-checking was not activated at config time (through --cfg=model-check:1). This won't work, sorry.");
+        ("You are specifying a value to enable/disable the detection of non progressive cycles after the initialization (through MSG_config?), but model-checking was not activated at config time (through bu the program was not runned under the model-checker (with simgrid-mc)). This won't work, sorry.");
   }
   _sg_mc_termination = xbt_cfg_get_boolean(_sg_cfg_set, name);
 }
index c8d9d8b..c942bdd 100644 (file)
@@ -14,6 +14,7 @@
 #include "mc/datatypes.h"
 #include "mc/mc_private.h"
 #include "mc/mc_snapshot.h"
+#include "mc/mc_dwarf.hpp"
 #include "mc/Type.hpp"
 
 using simgrid::mc::remote;
@@ -26,125 +27,12 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_diff, xbt,
 xbt_dynar_t mc_heap_comparison_ignore;
 xbt_dynar_t stacks_areas;
 
-
-
-/********************************* Backtrace ***********************************/
-/******************************************************************************/
-
-static void mmalloc_backtrace_block_display(void *heapinfo, int block)
-{
-
-  /* xbt_ex_t e; */
-
-  /* if (((malloc_info *)heapinfo)[block].busy_block.bt_size == 0) { */
-  /*   fprintf(stderr, "No backtrace available for that block, sorry.\n"); */
-  /*   return; */
-  /* } */
-
-  /* memcpy(&e.bt,&(((malloc_info *)heapinfo)[block].busy_block.bt),sizeof(void*)*XBT_BACKTRACE_SIZE); */
-  /* e.used = ((malloc_info *)heapinfo)[block].busy_block.bt_size; */
-
-  /* xbt_ex_setup_backtrace(&e); */
-  /* if (e.used == 0) { */
-  /*   fprintf(stderr, "(backtrace not set)\n"); */
-  /* } else if (e.bt_strings == NULL) { */
-  /*   fprintf(stderr, "(backtrace not ready to be computed. %s)\n",xbt_binary_name?"Dunno why":"xbt_binary_name not setup yet"); */
-  /* } else { */
-  /*   int i; */
-
-  /*   fprintf(stderr, "Backtrace of where the block %d was malloced (%d frames):\n", block ,e.used); */
-  /*   for (i = 0; i < e.used; i++)       /\* no need to display "xbt_backtrace_display" *\/{ */
-  /*     fprintf(stderr, "%d ---> %s\n",i, e.bt_strings[i] + 4); */
-  /*   } */
-  /* } */
-}
-
-static void mmalloc_backtrace_fragment_display(void *heapinfo, int block,
-                                               int frag)
-{
-
-  /* xbt_ex_t e; */
-
-  /* memcpy(&e.bt,&(((malloc_info *)heapinfo)[block].busy_frag.bt[frag]),sizeof(void*)*XBT_BACKTRACE_SIZE); */
-  /* e.used = XBT_BACKTRACE_SIZE; */
-
-  /* xbt_ex_setup_backtrace(&e); */
-  /* if (e.used == 0) { */
-  /*   fprintf(stderr, "(backtrace not set)\n"); */
-  /* } else if (e.bt_strings == NULL) { */
-  /*   fprintf(stderr, "(backtrace not ready to be computed. %s)\n",xbt_binary_name?"Dunno why":"xbt_binary_name not setup yet"); */
-  /* } else { */
-  /*   int i; */
-
-  /*   fprintf(stderr, "Backtrace of where the fragment %d in block %d was malloced (%d frames):\n", frag, block ,e.used); */
-  /*   for (i = 0; i < e.used; i++)       /\* no need to display "xbt_backtrace_display" *\/{ */
-  /*     fprintf(stderr, "%d ---> %s\n",i, e.bt_strings[i] + 4); */
-  /*   } */
-  /* } */
-
-}
-
-static void mmalloc_backtrace_display(void *addr)
-{
-
-  /* size_t block, frag_nb; */
-  /* int type; */
-
-  /* block = (((char*) (addr) - (char*) heap -> heapbase) / BLOCKSIZE + 1); */
-
-  /* type = heap->heapinfo[block].type; */
-
-  /* switch(type){ */
-  /* case MMALLOC_TYPE_HEAPINFO :  */
-  /* case MMALLOC_TYPE_FREE : /\* Free block *\/ */
-  /*   fprintf(stderr, "Asked to display the backtrace of a block that is free. I'm puzzled\n"); */
-  /*   xbt_abort(); */
-  /*   break;  */
-  /* case 0: /\* Large block *\/ */
-  /*   mmalloc_backtrace_block_display(heap->heapinfo, block); */
-  /*   break; */
-  /* default: /\* Fragmented block *\/ */
-  /*   frag_nb = RESIDUAL(addr, BLOCKSIZE) >> type; */
-  /*   if(heap->heapinfo[block].busy_frag.frag_size[frag_nb] == -1){ */
-  /*     fprintf(stderr , "Asked to display the backtrace of a fragment that is free. I'm puzzled\n"); */
-  /*     xbt_abort(); */
-  /*   } */
-  /*   mmalloc_backtrace_fragment_display(heap->heapinfo, block, frag_nb); */
-  /*   break; */
-  /* } */
-}
-
-
-static int compare_backtrace(int b1, int f1, int b2, int f2)
-{
-  /*int i = 0;
-     if(f1 != -1){
-     for(i=0; i< XBT_BACKTRACE_SIZE; i++){
-     if(heapinfo1[b1].busy_frag.bt[f1][i] != heapinfo2[b2].busy_frag.bt[f2][i]){
-     //mmalloc_backtrace_fragment_display((void*)heapinfo1, b1, f1);
-     //mmalloc_backtrace_fragment_display((void*)heapinfo2, b2, f2);
-     return 1;
-     }
-     }
-     }else{
-     for(i=0; i< heapinfo1[b1].busy_block.bt_size; i++){
-     if(heapinfo1[b1].busy_block.bt[i] != heapinfo2[b2].busy_block.bt[i]){
-     //mmalloc_backtrace_block_display((void*)heapinfo1, b1);
-     //mmalloc_backtrace_block_display((void*)heapinfo2, b2);
-     return 1;
-     }
-     }
-     } */
-  return 0;
-}
-
-
 /*********************************** Heap comparison ***********************************/
 /***************************************************************************************/
 
 typedef char *type_name;
 
-struct s_mc_diff {
+struct XBT_PRIVATE s_mc_diff {
   s_xbt_mheap_t std_heap_copy;
   size_t heaplimit;
   // Number of blocks in the heaps:
@@ -461,7 +349,7 @@ int mmalloc_compare_heap(mc_snapshot_t snapshot1, mc_snapshot_t snapshot2)
   const malloc_info* heapinfos2 = snapshot2->read<malloc_info*>(
     (std::uint64_t)heapinfo_address, simgrid::mc::ProcessIndexMissing);
 
-  while (i1 <= state->heaplimit) {
+  while (i1 < state->heaplimit) {
 
     const malloc_info* heapinfo1 = (const malloc_info*) MC_region_read(heap_region1, &heapinfo_temp1, &heapinfos1[i1], sizeof(malloc_info));
     const malloc_info* heapinfo2 = (const malloc_info*) MC_region_read(heap_region2, &heapinfo_temp2, &heapinfos2[i1], sizeof(malloc_info));
@@ -525,7 +413,7 @@ int mmalloc_compare_heap(mc_snapshot_t snapshot1, mc_snapshot_t snapshot2)
 
       }
 
-      while (i2 <= state->heaplimit && !equal) {
+      while (i2 < state->heaplimit && !equal) {
 
         addr_block2 = (ADDR2UINT(i2) - 1) * BLOCKSIZE +
                        (char *) state->std_heap_copy.heapbase;
@@ -610,7 +498,7 @@ int mmalloc_compare_heap(mc_snapshot_t snapshot1, mc_snapshot_t snapshot2)
 
         }
 
-        while (i2 <= state->heaplimit && !equal) {
+        while (i2 < state->heaplimit && !equal) {
 
           const malloc_info* heapinfo2b = (const malloc_info*) MC_region_read(
             heap_region2, &heapinfo_temp2b, &heapinfos2[i2],
@@ -684,7 +572,7 @@ int mmalloc_compare_heap(mc_snapshot_t snapshot1, mc_snapshot_t snapshot2)
   /* All blocks/fragments are equal to another block/fragment ? */
   size_t i = 1, j = 0;
 
-  for(i = 1; i <= state->heaplimit; i++) {
+  for(i = 1; i < state->heaplimit; i++) {
     const malloc_info* heapinfo1 = (const malloc_info*) MC_region_read(
       heap_region1, &heapinfo_temp1, &heapinfos1[i], sizeof(malloc_info));
     if (heapinfo1->type == MMALLOC_TYPE_UNFRAGMENTED) {
@@ -726,7 +614,7 @@ int mmalloc_compare_heap(mc_snapshot_t snapshot1, mc_snapshot_t snapshot2)
   if (i1 == state->heaplimit)
     XBT_DEBUG("Number of blocks/fragments not found in heap1 : %d", nb_diff1);
 
-  for (i=1; i <= state->heaplimit; i++) {
+  for (i=1; i < state->heaplimit; i++) {
     const malloc_info* heapinfo2 = (const malloc_info*) MC_region_read(
       heap_region2, &heapinfo_temp2, &heapinfos2[i], sizeof(malloc_info));
     if (heapinfo2->type == MMALLOC_TYPE_UNFRAGMENTED) {
@@ -1042,7 +930,7 @@ top:
         return -1;
       }
     } else {
-      for(simgrid::mc::Type& member : type->members) {
+      for(simgrid::mc::Member& member : type->members) {
         // TODO, optimize this? (for the offset case)
         void *real_member1 =
             mc_member_resolve(real_area1, type, &member, (simgrid::mc::AddressSpace*) snapshot1, process_index);
@@ -1051,7 +939,7 @@ top:
         res =
             compare_heap_area_with_type(state, process_index, real_member1, real_member2,
                                         snapshot1, snapshot2,
-                                        previous, member.subtype, -1,
+                                        previous, member.type, -1,
                                         check_ignore, 0);
         if (res == 1) {
           return res;
@@ -1103,18 +991,18 @@ static simgrid::mc::Type* get_offset_type(void *real_base_address, simgrid::mc::
       else
         return NULL;
     } else {
-      for(simgrid::mc::Type& member : type->members) {
+      for(simgrid::mc::Member& member : type->members) {
 
         if (member.has_offset_location()) {
           // We have the offset, use it directly (shortcut):
           if (member.offset() == offset)
-            return member.subtype;
+            return member.type;
         } else {
           void *real_member =
             mc_member_resolve(real_base_address, type, &member,
               snapshot, process_index);
           if ((char*) real_member - (char *) real_base_address == offset)
-            return member.subtype;
+            return member.type;
         }
 
       }
index 9283528..4d1aef5 100644 (file)
@@ -5,11 +5,12 @@
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
 #include <cinttypes>
+#include <cstdint>
 
 #include <algorithm>
 #include <memory>
 
-#include <stdlib.h>
+#include <cstdlib>
 #define DW_LANG_Objc DW_LANG_ObjC       /* fix spelling error in older dwarf.h */
 #include <dwarf.h>
 #include <elfutils/libdw.h>
@@ -23,8 +24,8 @@
 
 #include "mc_object_info.h"
 #include "mc_private.h"
-#include "mc_process.h"
 
+#include "mc/Process.hpp"
 #include "mc/ObjectInformation.hpp"
 #include "mc/Variable.hpp"
 
@@ -276,30 +277,26 @@ static const char *MC_dwarf_at_linkage_name(Dwarf_Die * die)
 static Dwarf_Off MC_dwarf_attr_dieoffset(Dwarf_Die * die, int attribute)
 {
   Dwarf_Attribute attr;
-  if (dwarf_hasattr_integrate(die, attribute)) {
-    dwarf_attr_integrate(die, attribute, &attr);
-    Dwarf_Die subtype_die;
-    if (dwarf_formref_die(&attr, &subtype_die) == NULL) {
-      xbt_die("Could not find DIE");
-    }
-    return dwarf_dieoffset(&subtype_die);
-  } else
+  if (dwarf_hasattr_integrate(die, attribute) == 0)
     return 0;
+  dwarf_attr_integrate(die, attribute, &attr);
+  Dwarf_Die subtype_die;
+  if (dwarf_formref_die(&attr, &subtype_die) == NULL)
+    xbt_die("Could not find DIE");
+  return dwarf_dieoffset(&subtype_die);
 }
 
 static Dwarf_Off MC_dwarf_attr_integrate_dieoffset(Dwarf_Die * die,
                                                    int attribute)
 {
   Dwarf_Attribute attr;
-  if (dwarf_hasattr_integrate(die, attribute)) {
-    dwarf_attr_integrate(die, DW_AT_type, &attr);
-    Dwarf_Die subtype_die;
-    if (dwarf_formref_die(&attr, &subtype_die) == NULL) {
-      xbt_die("Could not find DIE");
-    }
-    return dwarf_dieoffset(&subtype_die);
-  } else
+  if (dwarf_hasattr_integrate(die, attribute) == 0)
     return 0;
+  dwarf_attr_integrate(die, DW_AT_type, &attr);
+  Dwarf_Die subtype_die;
+  if (dwarf_formref_die(&attr, &subtype_die) == NULL)
+    xbt_die("Could not find DIE");
+  return dwarf_dieoffset(&subtype_die);
 }
 
 /** \brief Find the type/subtype (DW_AT_type) for a DIE
@@ -404,24 +401,22 @@ static uint64_t MC_dwarf_subrange_element_count(Dwarf_Die * die,
              MC_dwarf_die_tagname(die));
 
   // Use DW_TAG_count if present:
-  if (dwarf_hasattr_integrate(die, DW_AT_count)) {
+  if (dwarf_hasattr_integrate(die, DW_AT_count))
     return MC_dwarf_attr_integrate_uint(die, DW_AT_count, 0);
-  }
   // Otherwise compute DW_TAG_upper_bound-DW_TAG_lower_bound + 1:
 
-  if (!dwarf_hasattr_integrate(die, DW_AT_upper_bound)) {
+  if (!dwarf_hasattr_integrate(die, DW_AT_upper_bound))
     // This is not really 0, but the code expects this (we do not know):
     return 0;
-  }
+
   uint64_t upper_bound =
       MC_dwarf_attr_integrate_uint(die, DW_AT_upper_bound, -1);
 
   uint64_t lower_bound = 0;
-  if (dwarf_hasattr_integrate(die, DW_AT_lower_bound)) {
+  if (dwarf_hasattr_integrate(die, DW_AT_lower_bound))
     lower_bound = MC_dwarf_attr_integrate_uint(die, DW_AT_lower_bound, -1);
-  } else {
+  else
     lower_bound = MC_dwarf_default_lower_bound(dwarf_srclang(unit));
-  }
   return upper_bound - lower_bound + 1;
 }
 
@@ -447,9 +442,8 @@ static uint64_t MC_dwarf_array_element_count(Dwarf_Die * die, Dwarf_Die * unit)
        res = dwarf_siblingof(&child, &child)) {
     int child_tag = dwarf_tag(&child);
     if (child_tag == DW_TAG_subrange_type
-        || child_tag == DW_TAG_enumeration_type) {
+        || child_tag == DW_TAG_enumeration_type)
       result *= MC_dwarf_subrange_element_count(&child, unit);
-    }
   }
   return result;
 }
@@ -481,22 +475,19 @@ static bool MC_compare_variable(
  *  \param  member the member of the type
  *  \param  child  DIE of the member (DW_TAG_member)
  */
-static void MC_dwarf_fill_member_location(simgrid::mc::Type* type, simgrid::mc::Type* member,
-                                          Dwarf_Die * child)
+static void MC_dwarf_fill_member_location(
+  simgrid::mc::Type* type, simgrid::mc::Member* member, Dwarf_Die * child)
 {
-  if (dwarf_hasattr(child, DW_AT_data_bit_offset)) {
+  if (dwarf_hasattr(child, DW_AT_data_bit_offset))
     xbt_die("Can't groke DW_AT_data_bit_offset.");
-  }
 
   if (!dwarf_hasattr_integrate(child, DW_AT_data_member_location)) {
-    if (type->type != DW_TAG_union_type) {
-      xbt_die
-          ("Missing DW_AT_data_member_location field in DW_TAG_member %s of type <%"
-           PRIx64 ">%s", member->name.c_str(),
-           (uint64_t) type->id, type->name.c_str());
-    } else {
+    if (type->type == DW_TAG_union_type)
       return;
-    }
+    xbt_die
+        ("Missing DW_AT_data_member_location field in DW_TAG_member %s of type <%"
+         PRIx64 ">%s", member->name.c_str(),
+         (uint64_t) type->id, type->name.c_str());
   }
 
   Dwarf_Attribute attr;
@@ -510,13 +501,12 @@ static void MC_dwarf_fill_member_location(simgrid::mc::Type* type, simgrid::mc::
     {
       Dwarf_Op *expr;
       size_t len;
-      if (dwarf_getlocation(&attr, &expr, &len)) {
+      if (dwarf_getlocation(&attr, &expr, &len))
         xbt_die
             ("Could not read location expression DW_AT_data_member_location in DW_TAG_member %s of type <%"
              PRIx64 ">%s", MC_dwarf_attr_integrate_string(child, DW_AT_name),
              (uint64_t) type->id, type->name.c_str());
-      }
-      simgrid::mc::DwarfExpression(expr, expr+len);
+      member->location_expression = simgrid::mc::DwarfExpression(expr, expr+len);
       break;
     }
   case MC_DW_CLASS_CONSTANT:
@@ -571,31 +561,25 @@ static void MC_dwarf_add_members(simgrid::mc::ObjectInformation* info, Dwarf_Die
         continue;
 
       // TODO, we should use another type (because is is not a type but a member)
-      simgrid::mc::Type member;
-      member.type = tag;
-
-      // Global Offset:
-      member.id = dwarf_dieoffset(&child);
+      simgrid::mc::Member member;
+      member.inheritance = tag == DW_TAG_inheritance;
 
       const char *name = MC_dwarf_attr_integrate_string(&child, DW_AT_name);
       if (name)
         member.name = name;
       member.byte_size =
           MC_dwarf_attr_integrate_uint(&child, DW_AT_byte_size, 0);
-      member.element_count = -1;
       member.type_id = MC_dwarf_at_type(&child);
 
-      if (dwarf_hasattr(&child, DW_AT_data_bit_offset)) {
+      if (dwarf_hasattr(&child, DW_AT_data_bit_offset))
         xbt_die("Can't groke DW_AT_data_bit_offset.");
-      }
 
       MC_dwarf_fill_member_location(type, &member, &child);
 
-      if (!member.type_id) {
+      if (!member.type_id)
         xbt_die("Missing type for member %s of <%" PRIx64 ">%s",
                 member.name.c_str(),
                 (uint64_t) type->id, type->name.c_str());
-      }
 
       type->members.push_back(std::move(member));
     }
@@ -660,9 +644,8 @@ static simgrid::mc::Type MC_dwarf_die_to_type(
            || type.type == DW_TAG_structure_type
            || type.type == DW_TAG_class_type) {
     Dwarf_Word size;
-    if (dwarf_aggregate_size(die, &size) == 0) {
+    if (dwarf_aggregate_size(die, &size) == 0)
       type.byte_size = size;
-    }
   }
 
   switch (type.type) {
@@ -717,10 +700,9 @@ static std::unique_ptr<simgrid::mc::Variable> MC_die_to_variable(
     return nullptr;
 
   Dwarf_Attribute attr_location;
-  if (dwarf_attr(die, DW_AT_location, &attr_location) == NULL) {
+  if (dwarf_attr(die, DW_AT_location, &attr_location) == NULL)
     // No location: do not add it ?
     return nullptr;
-  }
 
   std::unique_ptr<simgrid::mc::Variable> variable =
     std::unique_ptr<simgrid::mc::Variable>(new simgrid::mc::Variable());
@@ -1002,26 +984,20 @@ void MC_dwarf_get_variables(simgrid::mc::ObjectInformation* info)
     xbt_die("Could not open file %s", info->file_name.c_str());
   Dwarf *dwarf = dwarf_begin(fd, DWARF_C_READ);
   if (dwarf == NULL)
-    xbt_die("Your program must be compiled with -g (%s)",
+    xbt_die("Missing debugging information in %s\n"
+      "Your program and its dependencies must have debugging information.\n"
+      "You might want to recompile with -g or install the suitable debugging package.\n",
       info->file_name.c_str());
   // For each compilation unit:
   Dwarf_Off offset = 0;
   Dwarf_Off next_offset = 0;
   size_t length;
+
   while (dwarf_nextcu(dwarf, offset, &next_offset, &length, NULL, NULL, NULL) ==
          0) {
     Dwarf_Die unit_die;
-    if (dwarf_offdie(dwarf, offset + length, &unit_die) != NULL) {
-
-      // For each child DIE:
-      Dwarf_Die child;
-      int res;
-      for (res = dwarf_child(&unit_die, &child); res == 0;
-           res = dwarf_siblingof(&child, &child)) {
-        MC_dwarf_handle_die(info, &child, &unit_die, NULL, NULL);
-      }
-
-    }
+    if (dwarf_offdie(dwarf, offset + length, &unit_die) != NULL)
+      MC_dwarf_handle_children(info, &unit_die, &unit_die, NULL, NULL);
     offset = next_offset;
   }
 
@@ -1073,10 +1049,9 @@ static void MC_post_process_variables(simgrid::mc::ObjectInformation* info)
     MC_compare_variable);
 
   for(simgrid::mc::Variable& variable : info->global_variables)
-    if (variable.type_id) {
+    if (variable.type_id)
       variable.type = simgrid::util::find_map_ptr(
         info->types, variable.type_id);
-    }
 }
 
 static void mc_post_process_scope(simgrid::mc::ObjectInformation* info, simgrid::mc::Frame* scope)
@@ -1087,16 +1062,15 @@ static void mc_post_process_scope(simgrid::mc::ObjectInformation* info, simgrid:
     auto i = info->subprograms.find(scope->abstract_origin_id);
     xbt_assert(i != info->subprograms.end(),
       "Could not lookup abstract origin %" PRIx64,
-      (uint64_t) scope->abstract_origin_id);
+      (std::uint64_t) scope->abstract_origin_id);
     scope->name = i->second.name;
   }
 
   // Direct:
   for (simgrid::mc::Variable& variable : scope->variables)
-    if (variable.type_id) {
+    if (variable.type_id)
       variable.type = simgrid::util::find_map_ptr(
         info->types, variable.type_id);
-    }
 
   // Recursive post-processing of nested-scopes:
   for (simgrid::mc::Frame& nested_scope : scope->scopes)
@@ -1104,34 +1078,40 @@ static void mc_post_process_scope(simgrid::mc::ObjectInformation* info, simgrid:
 
 }
 
-/** \brief Fill/lookup the "subtype" field.
- */
-static void MC_resolve_subtype(simgrid::mc::ObjectInformation* info, simgrid::mc::Type* type)
+static
+simgrid::mc::Type* MC_resolve_type(
+  simgrid::mc::ObjectInformation* info, unsigned type_id)
 {
-  if (!type->type_id)
-    return;
-  type->subtype = simgrid::util::find_map_ptr(info->types, type->type_id);
-  if (type->subtype == nullptr)
-    return;
-  if (type->subtype->byte_size != 0)
-    return;
-  if (type->subtype->name.empty())
-    return;
+  if (!type_id)
+    return nullptr;
+  simgrid::mc::Type* type = simgrid::util::find_map_ptr(info->types, type_id);
+  if (type == nullptr)
+    return nullptr;
+
+  // We already have the information on the type:
+  if (type->byte_size != 0)
+    return type;
+
+  // Don't have a name, we can't find a more complete version:
+  if (type->name.empty())
+    return type;
+
   // Try to find a more complete description of the type:
   // We need to fix in order to support C++.
   simgrid::mc::Type** subtype = simgrid::util::find_map_ptr(
-    info->full_types_by_name, type->subtype->name);
+    info->full_types_by_name, type->name);
   if (subtype)
-    type->subtype = *subtype;
+    type = *subtype;
+  return type;
 }
 
 static void MC_post_process_types(simgrid::mc::ObjectInformation* info)
 {
   // Lookup "subtype" field:
   for(auto& i : info->types) {
-    MC_resolve_subtype(info, &(i.second));
-    for (simgrid::mc::Type& member : i.second.members)
-      MC_resolve_subtype(info, &member);
+    i.second.subtype = MC_resolve_type(info, i.second.type_id);
+    for (simgrid::mc::Member& member : i.second.members)
+      member.type = MC_resolve_type(info, member.type_id);
   }
 }
 
@@ -1162,13 +1142,13 @@ void MC_post_process_object_info(simgrid::mc::Process* process, simgrid::mc::Obj
 
     simgrid::mc::Type* type = &(i.second);
     simgrid::mc::Type* subtype = type;
-    while (subtype->type == DW_TAG_typedef || subtype->type == DW_TAG_volatile_type
-      || subtype->type == DW_TAG_const_type) {
+    while (subtype->type == DW_TAG_typedef
+        || subtype->type == DW_TAG_volatile_type
+        || subtype->type == DW_TAG_const_type)
       if (subtype->subtype)
         subtype = subtype->subtype;
       else
         break;
-    }
 
     // Resolve full_type:
     if (!subtype->name.empty() && subtype->byte_size == 0) {
diff --git a/src/mc/mc_dwarf.hpp b/src/mc/mc_dwarf.hpp
new file mode 100644 (file)
index 0000000..41d4841
--- /dev/null
@@ -0,0 +1,216 @@
+/* Copyright (c) 2008-2015. The SimGrid Team.
+ * All rights reserved.                                                     */
+
+/* This program is free software; you can redistribute it and/or modify it
+ * under the terms of the license (GNU LGPL) which comes with this package. */
+
+#if !defined(SIMGRID_MC_DWARF_HPP)
+#define SIMGRID_MC_DWARF_HPP
+
+#include <memory>
+
+#include <string.h>
+
+#include <xbt/sysdep.h>
+
+#define DW_LANG_Objc DW_LANG_ObjC       /* fix spelling error in older dwarf.h */
+#include <dwarf.h>
+
+#include "mc/Variable.hpp"
+#include "mc/mc_memory_map.h"
+
+/** \brief A class of DWARF tags (DW_TAG_*)
+ */
+typedef enum mc_tag_class {
+  mc_tag_unknown,
+  mc_tag_type,
+  mc_tag_subprogram,
+  mc_tag_variable,
+  mc_tag_scope,
+  mc_tag_namespace
+} mc_tag_class;
+
+static mc_tag_class MC_dwarf_tag_classify(int tag)
+{
+  switch (tag) {
+
+  case DW_TAG_array_type:
+  case DW_TAG_class_type:
+  case DW_TAG_enumeration_type:
+  case DW_TAG_typedef:
+  case DW_TAG_pointer_type:
+  case DW_TAG_reference_type:
+  case DW_TAG_rvalue_reference_type:
+  case DW_TAG_string_type:
+  case DW_TAG_structure_type:
+  case DW_TAG_subroutine_type:
+  case DW_TAG_union_type:
+  case DW_TAG_ptr_to_member_type:
+  case DW_TAG_set_type:
+  case DW_TAG_subrange_type:
+  case DW_TAG_base_type:
+  case DW_TAG_const_type:
+  case DW_TAG_file_type:
+  case DW_TAG_packed_type:
+  case DW_TAG_volatile_type:
+  case DW_TAG_restrict_type:
+  case DW_TAG_interface_type:
+  case DW_TAG_unspecified_type:
+  case DW_TAG_shared_type:
+    return mc_tag_type;
+
+  case DW_TAG_subprogram:
+    return mc_tag_subprogram;
+
+  case DW_TAG_variable:
+  case DW_TAG_formal_parameter:
+    return mc_tag_variable;
+
+  case DW_TAG_lexical_block:
+  case DW_TAG_try_block:
+  case DW_TAG_catch_block:
+  case DW_TAG_inlined_subroutine:
+  case DW_TAG_with_stmt:
+    return mc_tag_scope;
+
+  case DW_TAG_namespace:
+    return mc_tag_namespace;
+
+  default:
+    return mc_tag_unknown;
+
+  }
+}
+
+#define MC_DW_CLASS_UNKNOWN 0
+#define MC_DW_CLASS_ADDRESS 1   // Location in the address space of the program
+#define MC_DW_CLASS_BLOCK 2     // Arbitrary block of bytes
+#define MC_DW_CLASS_CONSTANT 3
+#define MC_DW_CLASS_STRING 3    // String
+#define MC_DW_CLASS_FLAG 4      // Boolean
+#define MC_DW_CLASS_REFERENCE 5 // Reference to another DIE
+#define MC_DW_CLASS_EXPRLOC 6   // DWARF expression/location description
+#define MC_DW_CLASS_LINEPTR 7
+#define MC_DW_CLASS_LOCLISTPTR 8
+#define MC_DW_CLASS_MACPTR 9
+#define MC_DW_CLASS_RANGELISTPTR 10
+
+/** \brief Find the DWARF data class for a given DWARF data form
+ *
+ *  This mapping is defined in the DWARF spec.
+ *
+ *  \param form The form (values taken from the DWARF spec)
+ *  \return An internal representation for the corresponding class
+ * */
+static int MC_dwarf_form_get_class(int form)
+{
+  switch (form) {
+  case DW_FORM_addr:
+    return MC_DW_CLASS_ADDRESS;
+  case DW_FORM_block2:
+  case DW_FORM_block4:
+  case DW_FORM_block:
+  case DW_FORM_block1:
+    return MC_DW_CLASS_BLOCK;
+  case DW_FORM_data1:
+  case DW_FORM_data2:
+  case DW_FORM_data4:
+  case DW_FORM_data8:
+  case DW_FORM_udata:
+  case DW_FORM_sdata:
+    return MC_DW_CLASS_CONSTANT;
+  case DW_FORM_string:
+  case DW_FORM_strp:
+    return MC_DW_CLASS_STRING;
+  case DW_FORM_ref_addr:
+  case DW_FORM_ref1:
+  case DW_FORM_ref2:
+  case DW_FORM_ref4:
+  case DW_FORM_ref8:
+  case DW_FORM_ref_udata:
+    return MC_DW_CLASS_REFERENCE;
+  case DW_FORM_flag:
+  case DW_FORM_flag_present:
+    return MC_DW_CLASS_FLAG;
+  case DW_FORM_exprloc:
+    return MC_DW_CLASS_EXPRLOC;
+    // TODO sec offset
+    // TODO indirect
+  default:
+    return MC_DW_CLASS_UNKNOWN;
+  }
+}
+
+/** \brief Find the default lower bound for a given language
+ *
+ *  The default lower bound of an array (when DW_TAG_lower_bound
+ *  is missing) depends on the language of the compilation unit.
+ *
+ *  \param lang Language of the compilation unit (values defined in the DWARF spec)
+ *  \return     Default lower bound of an array in this compilation unit
+ * */
+static inline
+uint64_t MC_dwarf_default_lower_bound(int lang)
+{
+  switch (lang) {
+  case DW_LANG_C:
+  case DW_LANG_C89:
+  case DW_LANG_C99:
+  case DW_LANG_C_plus_plus:
+  case DW_LANG_D:
+  case DW_LANG_Java:
+  case DW_LANG_ObjC:
+  case DW_LANG_ObjC_plus_plus:
+  case DW_LANG_Python:
+  case DW_LANG_UPC:
+    return 0;
+  case DW_LANG_Ada83:
+  case DW_LANG_Ada95:
+  case DW_LANG_Fortran77:
+  case DW_LANG_Fortran90:
+  case DW_LANG_Fortran95:
+  case DW_LANG_Modula2:
+  case DW_LANG_Pascal83:
+  case DW_LANG_PL1:
+  case DW_LANG_Cobol74:
+  case DW_LANG_Cobol85:
+    return 1;
+  default:
+    xbt_die("No default DW_TAG_lower_bound for language %i and none given",
+            lang);
+    return 0;
+  }
+}
+
+/** Sort the variable by name and address.
+ *
+ *  We could use boost::container::flat_set instead.
+ */
+static inline
+bool MC_compare_variable(
+  simgrid::mc::Variable const& a, simgrid::mc::Variable const& b)
+{
+  int cmp = a.name.compare(b.name);
+  if (cmp < 0)
+    return true;
+  else if (cmp > 0)
+    return false;
+  else
+    return a.address < b.address;
+}
+
+XBT_PRIVATE std::shared_ptr<simgrid::mc::ObjectInformation> MC_find_object_info(
+  std::vector<simgrid::mc::VmMap> const& maps, const char* name, int executable);
+XBT_PRIVATE void MC_post_process_object_info(simgrid::mc::Process* process, simgrid::mc::ObjectInformation* info);
+
+XBT_PRIVATE void MC_dwarf_get_variables(simgrid::mc::ObjectInformation* info);
+XBT_PRIVATE void MC_dwarf_get_variables_libdw(simgrid::mc::ObjectInformation* info);
+
+XBT_PRIVATE const char* MC_dwarf_attrname(int attr);
+XBT_PRIVATE const char* MC_dwarf_tagname(int tag);
+
+XBT_PRIVATE void* mc_member_resolve(
+  const void* base, simgrid::mc::Type* type, simgrid::mc::Member* member,
+  simgrid::mc::AddressSpace* snapshot, int process_index);
+
+#endif
index d4926a2..cc9b6a6 100644 (file)
@@ -4,8 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include <stdint.h>
-#include <stdarg.h>
+#include <cstdint>
+#include <cstdarg>
 
 #include <dwarf.h>
 #include <elfutils/libdw.h>
@@ -38,10 +38,10 @@ static int mc_dwarf_push_value(mc_expression_state_t state, Dwarf_Off value)
  */
 static int mc_dwarf_register_to_libunwind(int dwarf_register)
 {
-#if defined(UNW_TARGET_X86_64)
+#if defined(__x86_64__)
   // It seems for this arch, DWARF and libunwind agree in the numbering:
   return dwarf_register;
-#elif defined(UNW_TARGET_X86)
+#elif defined(__i386__)
   // Could't find the authoritative source of information for this.
   // This is inspired from http://source.winehq.org/source/dlls/dbghelp/cpu_i386.c#L517.
   switch (dwarf_register) {
@@ -107,7 +107,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
   for (size_t i = 0; i != n; ++i) {
     int error = 0;
     const Dwarf_Op *op = ops + i;
-    uint8_t atom = op->atom;
+    std::uint8_t atom = op->atom;
 
     switch (atom) {
 
@@ -170,7 +170,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
         unw_step(&cursor);
 
         unw_word_t res;
-        unw_get_reg(&cursor, UNW_TDEP_SP, &res);
+        unw_get_reg(&cursor, UNW_REG_SP, &res);
         error = mc_dwarf_push_value(state, res);
         break;
       }
@@ -181,7 +181,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       {
         if (!state->frame_base)
           return MC_EXPRESSION_E_MISSING_FRAME_BASE;
-        uintptr_t fb = ((uintptr_t) state->frame_base) + op->number;
+        std::uintptr_t fb = ((std::uintptr_t) state->frame_base) + op->number;
         error = mc_dwarf_push_value(state, fb);
         break;
       }
@@ -233,7 +233,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
         return MC_EXPRESSION_E_NO_BASE_ADDRESS;
       if (state->stack_size == MC_EXPRESSION_STACK_SIZE)
         return MC_EXPRESSION_E_STACK_OVERFLOW;
-      Dwarf_Off addr = (Dwarf_Off) (uintptr_t)
+      Dwarf_Off addr = (Dwarf_Off) (std::uintptr_t)
         state->object_info->base_address() + op->number;
       error = mc_dwarf_push_value(state, addr);
       break;
@@ -279,7 +279,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t temp = state->stack[state->stack_size - 2];
+        std::uintptr_t temp = state->stack[state->stack_size - 2];
         state->stack[state->stack_size - 2] =
             state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 1] = temp;
@@ -302,7 +302,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t result =
+        std::uintptr_t result =
             state->stack[state->stack_size - 2] +
             state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 2] = result;
@@ -314,7 +314,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t result =
+        std::uintptr_t result =
             state->stack[state->stack_size - 2] -
             state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 2] = result;
@@ -350,7 +350,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t result =
+        std::uintptr_t result =
             state->stack[state->stack_size - 2] -
             state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 2] = result;
@@ -362,7 +362,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t result =
+        std::uintptr_t result =
             state->stack[state->stack_size -
                          2] & state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 2] = result;
@@ -374,7 +374,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t result =
+        std::uintptr_t result =
             state->stack[state->stack_size -
                          2] | state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 2] = result;
@@ -386,7 +386,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
       if (state->stack_size < 2)
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
-        uintptr_t result =
+        std::uintptr_t result =
             state->stack[state->stack_size -
                          2] ^ state->stack[state->stack_size - 1];
         state->stack[state->stack_size - 2] = result;
@@ -407,7 +407,7 @@ int mc_dwarf_execute_expression(size_t n, const Dwarf_Op * ops,
         return MC_EXPRESSION_E_STACK_UNDERFLOW;
       {
         // Computed address:
-        uintptr_t address = (uintptr_t) state->stack[state->stack_size - 1];
+        std::uintptr_t address = (std::uintptr_t) state->stack[state->stack_size - 1];
         if (!state->address_space)
           xbt_die("Missing address space");
         state->address_space->read_bytes(
@@ -546,10 +546,10 @@ void mc_dwarf_location_list_init(
 {
   list->clear();
 
-  ptrdiff_t offset = 0;
+  std::ptrdiff_t offset = 0;
   Dwarf_Addr base, start, end;
   Dwarf_Op *ops;
-  size_t len;
+  std::size_t len;
 
   while (1) {
 
index 8311eeb..983f111 100644 (file)
@@ -17,7 +17,7 @@
  *  \param tag tag code (see the DWARF specification)
  *  \return name of the tag
  */
-XBT_INTERNAL
+XBT_PRIVATE
 const char *MC_dwarf_tagname(int tag)
 {
   switch (tag) {
index f3b032b..5c704d4 100644 (file)
@@ -21,6 +21,7 @@ class AddressSpace;
 class Process;
 class Snapshot;
 class ObjectInformation;
+class Member;
 class Type;
 class Variable;
 class Frame;
index 23e7ab4..ccda078 100644 (file)
@@ -6,9 +6,10 @@
 
 #include <cinttypes>
 
-#include <assert.h>
-#include <string.h>
-#include <stdint.h>
+#include <cassert>
+#include <cstddef>
+#include <cstdint>
+#include <cstring>
 
 #include "mc_base.h"
 
@@ -507,6 +508,8 @@ void MC_print_statistics(mc_stats_t stats)
     if (_sg_mc_comms_determinism)
       XBT_INFO("Recv-deterministic : %s", !initial_global_state->recv_deterministic ? "No" : "Yes");
   }
+  if (getenv("SIMGRID_MC_SYSTEM_STATISTICS"))
+    system("free");
 }
 
 void MC_automaton_load(const char *file)
@@ -540,7 +543,7 @@ void MC_dump_stacks(FILE* file)
       unw_get_reg(&c, UNW_X86_64_RIP, &rip);
       unw_get_reg(&c, UNW_X86_64_RSP, &rsp);
       fprintf(file, "  %i: %s (RIP=0x%" PRIx64 " RSP=0x%" PRIx64 ")\n",
-        nframe, name, rip, rsp);
+        nframe, name, (std::uint64_t) rip, (std::uint64_t) rsp);
 #else
       fprintf(file, "  %i: %s\n", nframe, name);
 #endif
index eac6cc9..7a0249d 100644 (file)
 
 #include <cinttypes>
 
-#include <stdint.h>
-#include <stdbool.h>
+#include <cstdint>
 
 #include "mc_private.h"
 #include "mc/datatypes.h"
-#include <mc/mc.h>
 #include "mc_hash.hpp"
+#include <mc/mc.h>
 
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_hash, mc, "Logging specific to mc_hash");
 
 namespace simgrid {
 namespace mc {
 
-// This is djb2:
-#define MC_HASH_INIT ((simgrid::mc::hash_type)5381)
-
-template<class T>
-static void hash_update(hash_type& hash, T const& value)
-{
-  hash = (hash << 5) + hash + (uint64_t) value;
-}
-
-// ***** Hash state
-
-#if 0
-typedef struct s_mc_hashing_state {
-  // Set of pointers/addresses already processed (avoid loops):
-  mc_address_set_t handled_addresses;
-} mc_hashing_state;
-
-void mc_hash_state_init(mc_hashing_state * state);
-void mc_hash_state_destroy(mc_hashing_state * state);
-
-void mc_hash_state_init(mc_hashing_state * state)
-{
-  state->handled_addresses = mc_address_set_new();
-}
+namespace {
 
-void mc_hash_state_destroy(mc_hashing_state * state)
-{
-  mc_address_set_free(&state->handled_addresses);
-}
-
-// TODO, detect and avoid loops
-
-static bool mc_ignored(const void *address, size_t size)
-{
-  mc_heap_ignore_region_t region;
-  unsigned int cursor = 0;
-  const void *end = (char *) address + size;
-  xbt_dynar_foreach(mc_heap_comparison_ignore, cursor, region) {
-    void *istart = region->address;
-    void *iend = (char *) region->address + region->size;
-
-    if (address >= istart && address < iend && end >= istart && end < iend)
-      return true;
+class djb_hash {
+  hash_type state_ = 5381ll;
+public:
+  template<class T>
+  void update(T& x)
+  {
+    state_ = (state_ << 5) + state_ + (std::uint64_t) value;
   }
-
-  return false;
-}
-
-static void mc_hash_binary(hash_type * hash, const void *s, size_t len)
-{
-  const char *p = (const char*) s;
-  for (size_t i = 0; i != len; ++i) {
-    hash_update(*hash, p[i]);
+  hash_type value()
+  {
+    return state_;
   }
-}
-
-/** \brief Compute a hash for a given value of a given type
- *
- *  We try to be very conservative (do not hash too ambiguous things).
- *
- *  \param address address of the variable
- *  \param type type of the variable
- * */
-static void mc_hash_value(hash_type * hash, mc_hashing_state * state,
-                          simgrid::mc::ObjectInformation* info, const void *address,
-                          simgrid::mc::Type* type)
-{
-  simgrid::mc::Process* process = &mc_model_checker->process();
-top:
-
-  switch (type->type) {
-
-    // Not relevant, do nothing:
-  case DW_TAG_unspecified_type:
-    return;
-
-    // Simple case, hash this has binary:
-  case DW_TAG_base_type:
-  case DW_TAG_enumeration_type:
-    {
-      if (mc_ignored(address, 1))
-        return;
-      mc_hash_binary(hash, address, type->byte_size);
-      return;
-    }
-
-  case DW_TAG_array_type:
-    {
-      if (mc_ignored(address, type->byte_size))
-        return;
-
-      long element_count = type->element_count;
-      simgrid::mc::Type* subtype = type->subtype;
-      if (subtype == NULL) {
-        XBT_DEBUG("Hash array without subtype");
-        return;
-      }
-      int i;
-      for (i = 0; i != element_count; ++i) {
-        XBT_DEBUG("Hash array element %i", i);
-        void *subaddress = ((char *) address) + i * subtype->byte_size;
-        mc_hash_value(hash, state, info, subaddress, subtype);
-      }
-      return;
-    }
-
-    // Get the raw type:
-  case DW_TAG_typedef:
-  case DW_TAG_volatile_type:
-  case DW_TAG_const_type:
-  case DW_TAG_restrict_type:
-    {
-      type = type->subtype;
-      if (type == NULL)
-        return;
-      else
-        goto top;
-    }
-
-  case DW_TAG_structure_type:
-  case DW_TAG_class_type:
-    {
-      if (mc_ignored(address, type->byte_size))
-        return;
-
-      unsigned int cursor = 0;
-      simgrid::mc::Type* member;
-      xbt_dynar_foreach(type->members, cursor, member) {
-        XBT_DEBUG("Hash struct member %s", member->name);
-        if (type->subtype == NULL)
-          return;
-        void *member_variable = mc_member_resolve(address, type, member, NULL);
-        mc_hash_value(hash, state, info, member_variable, type->subtype);
-      }
-      return;
-    }
-
-    // Pointer, we hash a single value but it might be an array.
-  case DW_TAG_pointer_type:
-  case DW_TAG_reference_type:
-  case DW_TAG_rvalue_reference_type:
-    {
-      if (mc_ignored(address, 1))
-        return;
-
-      void *pointed = *(void **) address;
-      if (pointed == NULL) {
-        XBT_DEBUG("Hashed pinter is NULL");
-        return;
-      }
-      // Avoid loops:
-      if (mc_address_test(state->handled_addresses, pointed)) {
-        XBT_DEBUG("Hashed pointed data %p already hashed", pointed);
-        return;
-      }
-      mc_address_add(state->handled_addresses, pointed);
-
-      // Anything outside the R/W segments and the heap is not hashed:
-      bool valid_pointer = (pointed >= (void *) binary_info->start_rw
-                            && pointed <= (void *) binary_info->end_rw)
-          || (pointed >= (void *) libsimgrid_info->start_rw
-              && pointed <= (void *) libsimgrid_info->end_rw)
-          || (pointed >= process->heap_address
-              && pointed < (void *) ((const char *) process->heap_address + STD_HEAP_SIZE));
-      if (!valid_pointer) {
-        XBT_DEBUG("Hashed pointed data %p is in an ignored range", pointed);
-        return;
-      }
-
-      if (type->subtype == NULL) {
-        XBT_DEBUG("Missing type for %p (type=%s)",
-          pointed, type->type_id.c_str());
-        return;
-      }
-
-      address = pointed;
-      type = type->subtype;
-      goto top;
-    }
-
-    // Skip this:
-  case DW_TAG_union_type:
-  case DW_TAG_subroutine_type:
-  default:
-    return;
-  }
-}
-
-static void mc_hash_object_globals(hash_type * hash, mc_hashing_state * state,
-                                   simgrid::mc::ObjectInformation* info)
-{
-  unsigned int cursor = 0;
-  simgrid::mc::Variable* variable;
-  xbt_dynar_foreach(info->global_variables, cursor, variable) {
-    XBT_DEBUG("Hash global variable %s", variable->name);
-
-    if (variable->type_id == NULL) {
-      // Nothing
-      continue;
-    }
-
-    simgrid::mc::Type* type = variable->type;
-    if (type == NULL) {
-      // Nothing
-      continue;
-    }
-
-    const char *address = variable->address;
-    bool valid_pointer = (address >= binary_info->start_rw
-                          && address <= binary_info->end_rw)
-        || (address >= libsimgrid_info->start_rw
-            && address <= libsimgrid_info->end_rw)
-        || (address >= (const char *) process->heap_address
-            && address < (const char *) process->heap_address + STD_HEAP_SIZE);
-    if (!valid_pointer)
-      continue;
-
-    mc_hash_value(hash, state, info, variable->address, type);
-  }
-}
-
-static void mc_hash_stack_frame(mc_hash_t * hash,
-                                simgrid::mc::ObjectInformation* info,
-                                unw_cursor_t * unw_cursor, simgrid::mc::Frame* frame,
-                                char *frame_pointer, mc_hashing_state * state)
-{
-
-  // return; // TEMP
-
-  unsigned int cursor = 0;
-  simgrid::mc::Variable* variable;
-  xbt_dynar_foreach(frame->variables, cursor, variable) {
-
-    if (variable->type_id == NULL) {
-      XBT_DEBUG("Hash local variable %s without type", variable->name);
-      continue;
-    }
-    if (variable->locations.size == 0) {
-      XBT_DEBUG("Hash local variable %s without location", variable->name);
-      continue;
-    }
-
-    XBT_DEBUG("Hash local variable %s", variable->name);
-
-    void *variable_address =
-        (void *) mc_dwarf_resolve_locations(&variable->locations,
-                                            variable->object_info, unw_cursor,
-                                            frame_pointer, NULL);
-
-    simgrid::mc::Type* type = variable->type;
-    if (type == NULL) {
-      XBT_DEBUG("Hash local variable %s without loctypeation", variable->name);
-      continue;
-    }
-
-    mc_hash_value(hash, state, info, variable_address, type);
-  }
-
-  // TODO, handle nested scopes
-}
-
-static void mc_hash_stack(mc_hash_t * hash, mc_snapshot_stack_t stack,
-                          mc_hashing_state * state)
-{
-
-  unsigned cursor = 0;
-  mc_stack_frame_t stack_frame;
-
-  for(s_mc_stack_frame_t const& stack_frame : stack->stack_frames) {
-
-    hash_update(*hash, stack_frame.ip);
-
-    simgrid::mc::ObjectInformation* info;
-    if (stack_frame.ip >= (unw_word_t) libsimgrid_info->start_exec
-        && stack_frame.ip < (unw_word_t) libsimgrid_info->end_exec)
-      info = libsimgrid_info;
-    else if (stack_frame.ip >= (unw_word_t) binary_info->start_exec
-             && stack_frame.ip < (unw_word_t) binary_info->end_exec)
-      info = binary_info;
-    else
-      continue;
-
-    mc_hash_stack_frame(hash, info, &(stack_frame.unw_cursor),
-                        stack_frame.frame, (void *) stack_frame.frame_base,
-                        state);
-
-  }
-}
-
-static void mc_hash_stacks(mc_hash_t * hash, mc_hashing_state * state,
-                           xbt_dynar_t stacks)
-{
-  unsigned int cursor = 0;
-  mc_snapshot_stack_t current_stack;
-
-  hash_update(*hash, xbt_dynar_length(stacks_areas));
-
-  int i = 0;
-  xbt_dynar_foreach(stacks, cursor, current_stack) {
-    XBT_DEBUG("Stack %i", i);
-    mc_hash_stack(hash, current_stack, state);
-    ++i;
-  }
-}
-#endif
-
-static hash_type hash(std::vector<s_mc_snapshot_stack_t> const& stacks)
-{
-#if 0
-  mc_hashing_state state;
-  mc_hash_state_init(&state);
-#endif
-
-  hash_type hash = MC_HASH_INIT;
-
-  hash_update(hash, xbt_swag_size(simix_global->process_list));
-#if 0
-  // mc_hash_object_globals(&hash, &state, binary_info);
-  // mc_hash_object_globals(&hash, &state, libsimgrid_info);
-  // mc_hash_stacks(&hash, &state, stacks);
-  mc_hash_state_destroy(&state);
-#endif
-
+};
 
-  return hash;
 }
 
 hash_type hash(Snapshot const& snapshot)
 {
   XBT_DEBUG("START hash %i", snapshot.num_state);
-  hash_type res = simgrid::mc::hash(snapshot.stacks);
+  djb_hash hash;
+  // TODO, nb_processes
+  // TODO, heap_bytes_used
+  // TODO, root variables
+  // TODO, basic stack frame information
+  // TODO, stack frame local variables
   XBT_DEBUG("END hash %i", snapshot.num_state);
-  return res;
+  return hash.value();
 }
 
 }
index 20aea04..4a8dd6a 100644 (file)
@@ -17,7 +17,8 @@ namespace simgrid {
 namespace mc {
 
 typedef std::uint64_t hash_type;
-XBT_INTERNAL hash_type hash(simgrid::mc::Snapshot const& snapshot);
+
+XBT_PRIVATE hash_type hash(simgrid::mc::Snapshot const& snapshot);
 
 }
 }
index 38ff43b..a9b134d 100644 (file)
 #include <xbt/dynar.h>
 
 #include "mc/datatypes.h"
-#include "mc_process.h"
+#include "mc/Process.hpp"
 
 #include "xbt/misc.h"           /* SG_BEGIN_DECL */
 
 SG_BEGIN_DECL();
 
-XBT_INTERNAL void MC_stack_area_add(stack_region_t stack_area);
+XBT_PRIVATE void MC_stack_area_add(stack_region_t stack_area);
 
-XBT_INTERNAL xbt_dynar_t MC_checkpoint_ignore_new(void);
+XBT_PRIVATE xbt_dynar_t MC_checkpoint_ignore_new(void);
 
 SG_END_DECL();
 
index 1c0f58c..e350c86 100644 (file)
@@ -17,9 +17,9 @@
 
 SG_BEGIN_DECL()
 
-extern XBT_INTERNAL xbt_automaton_t _mc_property_automaton;
+extern XBT_PRIVATE xbt_automaton_t _mc_property_automaton;
 
-typedef struct s_mc_pair{
+typedef struct XBT_PRIVATE s_mc_pair {
   int num;
   int search_cycle;
   mc_state_t graph_state; /* System state included */
@@ -31,7 +31,7 @@ typedef struct s_mc_pair{
   int visited_pair_removed;
 } s_mc_pair_t, *mc_pair_t;
 
-typedef struct s_mc_visited_pair{
+typedef struct XBT_PRIVATE s_mc_visited_pair{
   int num;
   int other_num; /* Dot output for */
   int acceptance_pair;
@@ -44,17 +44,17 @@ typedef struct s_mc_visited_pair{
   int visited_removed;
 } s_mc_visited_pair_t, *mc_visited_pair_t;
 
-XBT_INTERNAL mc_pair_t MC_pair_new(void);
-XBT_INTERNAL void MC_pair_delete(mc_pair_t);
-XBT_INTERNAL mc_visited_pair_t MC_visited_pair_new(int pair_num, xbt_automaton_state_t automaton_state, xbt_dynar_t atomic_propositions, mc_state_t graph_state);
-XBT_INTERNAL void MC_visited_pair_delete(mc_visited_pair_t p);
+XBT_PRIVATE mc_pair_t MC_pair_new(void);
+XBT_PRIVATE void MC_pair_delete(mc_pair_t);
+XBT_PRIVATE mc_visited_pair_t MC_visited_pair_new(int pair_num, xbt_automaton_state_t automaton_state, xbt_dynar_t atomic_propositions, mc_state_t graph_state);
+XBT_PRIVATE void MC_visited_pair_delete(mc_visited_pair_t p);
 
 void MC_modelcheck_liveness(void);
-XBT_INTERNAL void MC_show_stack_liveness(xbt_fifo_t stack);
-XBT_INTERNAL void MC_dump_stack_liveness(xbt_fifo_t stack);
+XBT_PRIVATE void MC_show_stack_liveness(xbt_fifo_t stack);
+XBT_PRIVATE void MC_dump_stack_liveness(xbt_fifo_t stack);
 
-XBT_INTERNAL extern xbt_dynar_t visited_pairs;
-XBT_INTERNAL int is_visited_pair(mc_visited_pair_t visited_pair, mc_pair_t pair);
+XBT_PRIVATE extern xbt_dynar_t visited_pairs;
+XBT_PRIVATE int is_visited_pair(mc_visited_pair_t visited_pair, mc_pair_t pair);
 
 SG_END_DECL()
 
index 36757bb..1f82a16 100644 (file)
@@ -90,18 +90,18 @@ enum mc_location_type mc_get_location_type(mc_location_t location) {
   }
 }
 
-XBT_INTERNAL void mc_dwarf_resolve_location(
+XBT_PRIVATE void mc_dwarf_resolve_location(
   mc_location_t location, simgrid::mc::DwarfExpression* expression,
   simgrid::mc::ObjectInformation* object_info, unw_cursor_t* c,
   void* frame_pointer_address, simgrid::mc::AddressSpace* address_space,
   int process_index);
-MC_SHOULD_BE_INTERNAL void mc_dwarf_resolve_locations(
+void mc_dwarf_resolve_locations(
   mc_location_t location, simgrid::mc::LocationList* locations,
   simgrid::mc::ObjectInformation* object_info, unw_cursor_t* c,
   void* frame_pointer_address, simgrid::mc::AddressSpace* address_space,
   int process_index);
 
-XBT_INTERNAL void mc_dwarf_location_list_init(
+XBT_PRIVATE void mc_dwarf_location_list_init(
   simgrid::mc::LocationList*, simgrid::mc::ObjectInformation* info, Dwarf_Die* die,
   Dwarf_Attribute* attr);
 
@@ -126,10 +126,9 @@ typedef struct s_mc_expression_state {
   int process_index;
 } s_mc_expression_state_t, *mc_expression_state_t;
 
-MC_SHOULD_BE_INTERNAL int mc_dwarf_execute_expression(
+XBT_PUBLIC(int) mc_dwarf_execute_expression(
   size_t n, const Dwarf_Op* ops, mc_expression_state_t state);
-
-MC_SHOULD_BE_INTERNAL void* mc_find_frame_base(
+void* mc_find_frame_base(
   simgrid::mc::Frame* frame, simgrid::mc::ObjectInformation* object_info, unw_cursor_t* unw_cursor);
 
 SG_END_DECL()
@@ -137,7 +136,7 @@ SG_END_DECL()
 namespace simgrid {
 namespace mc {
 
-inline
+static inline
 int execute(DwarfExpression const& expression, mc_expression_state_t state)
 {
   return mc_dwarf_execute_expression(
index 29fe1f5..2dc276b 100644 (file)
@@ -18,8 +18,9 @@
  * @param snapshot Snapshot (or NULL)
  * @return Process address of the given member of the 'object' struct/class
  */
-void *mc_member_resolve(const void *base, simgrid::mc::Type* type, simgrid::mc::Type* member,
-                        simgrid::mc::AddressSpace* address_space, int process_index)
+void *mc_member_resolve(
+    const void *base, simgrid::mc::Type* type, simgrid::mc::Member* member,
+    simgrid::mc::AddressSpace* address_space, int process_index)
 {
   // TODO, get rid of this?
   if (!member->has_offset_location())
index 1a52bff..7860854 100644 (file)
@@ -34,14 +34,14 @@ struct VmMap {
   std::string pathname;         /* Path name of the mapped file */
 };
 
-std::vector<VmMap> get_memory_map(pid_t pid);
+XBT_PRIVATE std::vector<VmMap> get_memory_map(pid_t pid);
 
 }
 }
 
 extern "C" {
 
-XBT_INTERNAL void MC_find_object_address(
+XBT_PRIVATE void MC_find_object_address(
   std::vector<simgrid::mc::VmMap> const& maps, simgrid::mc::ObjectInformation* result);
 
 }
index cb9a6a2..019c758 100644 (file)
 #include "mc_forward.hpp"
 #include "mc_memory_map.h"
 
-XBT_INTERNAL std::shared_ptr<simgrid::mc::ObjectInformation> MC_find_object_info(
+XBT_PRIVATE std::shared_ptr<simgrid::mc::ObjectInformation> MC_find_object_info(
   std::vector<simgrid::mc::VmMap> const& maps, const char* name, int executable);
-XBT_INTERNAL void MC_post_process_object_info(simgrid::mc::Process* process, simgrid::mc::ObjectInformation* info);
+XBT_PRIVATE  void MC_post_process_object_info(simgrid::mc::Process* process, simgrid::mc::ObjectInformation* info);
 
-XBT_INTERNAL void MC_dwarf_get_variables(simgrid::mc::ObjectInformation* info);
-XBT_INTERNAL void MC_dwarf_get_variables_libdw(simgrid::mc::ObjectInformation* info);
+XBT_PRIVATE  void MC_dwarf_get_variables(simgrid::mc::ObjectInformation* info);
+XBT_PRIVATE  void MC_dwarf_get_variables_libdw(simgrid::mc::ObjectInformation* info);
 
-XBT_INTERNAL const char* MC_dwarf_attrname(int attr);
-XBT_INTERNAL const char* MC_dwarf_tagname(int tag);
-
-XBT_INTERNAL void* mc_member_resolve(
-  const void* base, simgrid::mc::Type* type, simgrid::mc::Type* member,
-  simgrid::mc::AddressSpace* snapshot, int process_index);
+XBT_PRIVATE  const char* MC_dwarf_attrname(int attr);
+XBT_PRIVATE  const char* MC_dwarf_tagname(int tag);
 
 #endif
index 2efe58b..b180c40 100644 (file)
@@ -15,6 +15,9 @@
 
 #include <xbt/mmalloc.h>
 
+#define SOFT_DIRTY_BIT_NUMBER 55
+#define SOFT_DIRTY (((uint64_t)1) << SOFT_DIRTY_BIT_NUMBER)
+
 using simgrid::mc::remote;
 
 namespace simgrid {
@@ -27,7 +30,8 @@ namespace mc {
  *  @return                Snapshot page numbers of this new snapshot
  */
 PerPageCopy::PerPageCopy(PageStore& store, AddressSpace& as,
-    remote_ptr<void> addr, std::size_t page_count)
+    remote_ptr<void> addr, std::size_t page_count,
+    const size_t* ref_page_numbers, const std::uint64_t* pagemap)
 {
   store_ = &store;
   this->pagenos_.resize(page_count);
@@ -35,6 +39,13 @@ PerPageCopy::PerPageCopy(PageStore& store, AddressSpace& as,
 
   for (size_t i = 0; i != page_count; ++i) {
 
+    // We don't have to compare soft-clean pages:
+    if (ref_page_numbers && pagemap && !(pagemap[i] & SOFT_DIRTY)) {
+      pagenos_[i] = ref_page_numbers[i];
+      store_->ref_page(ref_page_numbers[i]);
+      continue;
+    }
+
       remote_ptr<void> page = remote(addr.address() + (i << xbt_pagebits));
       xbt_assert(mc_page_offset((void*)page.address())==0,
         "Not at the beginning of a page");
index f5acc25..bbd2a64 100644 (file)
@@ -33,6 +33,7 @@
 #include <simgrid/msg.h>
 #include "xbt/strbuff.h"
 #include "xbt/parmap.h"
+#include <xbt/base.h>
 
 #include "mc_forward.h"
 #include "mc_protocol.h"
@@ -50,28 +51,28 @@ typedef struct s_mc_function_index_item s_mc_function_index_item_t, *mc_function
  */
 void MC_init_model_checker(pid_t pid, int socket);
 
-XBT_INTERNAL extern FILE *dot_output;
-XBT_INTERNAL extern const char* colors[13];
-XBT_INTERNAL extern xbt_parmap_t parmap;
+XBT_PRIVATE extern FILE *dot_output;
+XBT_PRIVATE extern const char* colors[13];
+XBT_PRIVATE extern xbt_parmap_t parmap;
 
-XBT_INTERNAL extern int user_max_depth_reached;
+XBT_PRIVATE extern int user_max_depth_reached;
 
-XBT_INTERNAL int MC_deadlock_check(void);
-XBT_INTERNAL void MC_replay(xbt_fifo_t stack);
-XBT_INTERNAL void MC_replay_liveness(xbt_fifo_t stack);
-XBT_INTERNAL void MC_show_deadlock(smx_simcall_t req);
-XBT_INTERNAL void MC_show_stack_safety(xbt_fifo_t stack);
-XBT_INTERNAL void MC_dump_stack_safety(xbt_fifo_t stack);
-XBT_INTERNAL void MC_show_non_termination(void);
+XBT_PRIVATE int MC_deadlock_check(void);
+XBT_PRIVATE void MC_replay(xbt_fifo_t stack);
+XBT_PRIVATE void MC_replay_liveness(xbt_fifo_t stack);
+XBT_PRIVATE void MC_show_deadlock(smx_simcall_t req);
+XBT_PRIVATE void MC_show_stack_safety(xbt_fifo_t stack);
+XBT_PRIVATE void MC_dump_stack_safety(xbt_fifo_t stack);
+XBT_PRIVATE void MC_show_non_termination(void);
 
 /** Stack (of `mc_state_t`) representing the current position of the
  *  the MC in the exploration graph
  *
  *  It is managed by its head (`xbt_fifo_shift` and `xbt_fifo_unshift`).
  */
-XBT_INTERNAL extern xbt_fifo_t mc_stack;
+XBT_PRIVATE extern xbt_fifo_t mc_stack;
 
-XBT_INTERNAL int get_search_interval(xbt_dynar_t list, void *ref, int *min, int *max);
+XBT_PRIVATE int get_search_interval(xbt_dynar_t list, void *ref, int *min, int *max);
 
 
 /****************************** Statistics ************************************/
@@ -85,9 +86,9 @@ typedef struct mc_stats {
   unsigned long executed_transitions;
 } s_mc_stats_t, *mc_stats_t;
 
-XBT_INTERNAL extern mc_stats_t mc_stats;
+XBT_PRIVATE extern mc_stats_t mc_stats;
 
-XBT_INTERNAL void MC_print_statistics(mc_stats_t stats);
+XBT_PRIVATE void MC_print_statistics(mc_stats_t stats);
 
 /********************************** Snapshot comparison **********************************/
 
@@ -100,22 +101,22 @@ typedef struct s_mc_comparison_times{
   double stacks_comparison_time;
 }s_mc_comparison_times_t, *mc_comparison_times_t;
 
-extern XBT_INTERNAL __thread mc_comparison_times_t mc_comp_times;
-extern XBT_INTERNAL __thread double mc_snapshot_comparison_time;
+extern XBT_PRIVATE __thread mc_comparison_times_t mc_comp_times;
+extern XBT_PRIVATE __thread double mc_snapshot_comparison_time;
 
-XBT_INTERNAL int snapshot_compare(void *state1, void *state2);
-XBT_INTERNAL void print_comparison_times(void);
+XBT_PRIVATE int snapshot_compare(void *state1, void *state2);
+XBT_PRIVATE void print_comparison_times(void);
 
 //#define MC_DEBUG 1
 #define MC_VERBOSE 1
 
 /********************************** Miscellaneous **********************************/
 
-XBT_INTERNAL void MC_dump_stacks(FILE* file);
+XBT_PRIVATE void MC_dump_stacks(FILE* file);
 
-XBT_INTERNAL void MC_report_assertion_error(void);
+XBT_PRIVATE void MC_report_assertion_error(void);
 
-XBT_INTERNAL void MC_invalidate_cache(void);
+XBT_PRIVATE void MC_invalidate_cache(void);
 
 SG_END_DECL()
 
index 702b94a..1c39fa7 100644 (file)
@@ -103,13 +103,13 @@ typedef struct s_mc_register_symbol_message {
   void* data;
 } s_mc_register_symbol_message_t, * mc_register_symbol_message_t;
 
-XBT_INTERNAL int MC_protocol_send(int socket, const void* message, size_t size);
-XBT_INTERNAL int MC_protocol_send_simple_message(int socket, e_mc_message_type type);
-XBT_INTERNAL int MC_protocol_hello(int socket);
-XBT_INTERNAL ssize_t MC_receive_message(int socket, void* message, size_t size, int options);
+XBT_PRIVATE int MC_protocol_send(int socket, const void* message, size_t size);
+XBT_PRIVATE int MC_protocol_send_simple_message(int socket, e_mc_message_type type);
+XBT_PRIVATE int MC_protocol_hello(int socket);
+XBT_PRIVATE ssize_t MC_receive_message(int socket, void* message, size_t size, int options);
 
-XBT_INTERNAL const char* MC_message_type_name(e_mc_message_type type);
-XBT_INTERNAL const char* MC_mode_name(e_mc_mode_t mode);
+XBT_PRIVATE const char* MC_message_type_name(e_mc_message_type type);
+XBT_PRIVATE const char* MC_mode_name(e_mc_mode_t mode);
 
 SG_END_DECL()
 
index d6f1097..53fe654 100644 (file)
@@ -4,8 +4,9 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include <stdio.h>
-#include <stdlib.h>
+#include <cstring>
+#include <cstdio>
+#include <cstdlib>
 
 #include <xbt.h>
 #include <simgrid/simix.h>
@@ -26,9 +27,9 @@ extern "C" {
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_record, mc,
   " Logging specific to MC record/replay facility");
 
-char* MC_record_path = NULL;
+char* MC_record_path = nullptr;
 
-void MC_record_replay(mc_record_item_t start, size_t len)
+void MC_record_replay(mc_record_item_t start, std::size_t len)
 {
   MC_wait_for_requests();
   mc_record_item_t end = start + len;
@@ -62,9 +63,9 @@ xbt_dynar_t MC_record_from_string(const char* data)
 {
   XBT_INFO("path=%s", data);
   if (!data || !data[0])
-    return NULL;
+    return nullptr;
 
-  xbt_dynar_t dynar = xbt_dynar_new(sizeof(s_mc_record_item_t), NULL);
+  xbt_dynar_t dynar = xbt_dynar_new(sizeof(s_mc_record_item_t), nullptr);
 
   const char* current = data;
   while (*current) {
@@ -76,8 +77,8 @@ xbt_dynar_t MC_record_from_string(const char* data)
     xbt_dynar_push(dynar, &item);
 
     // Find next chunk:
-    const char* end = strchr(current, ';');
-    if(end==NULL)
+    const char* end = std::strchr(current, ';');
+    if(end == nullptr)
       break;
     else
       current = end + 1;
@@ -87,15 +88,15 @@ xbt_dynar_t MC_record_from_string(const char* data)
 
 fail:
   xbt_dynar_free(&dynar);
-  return NULL;
+  return nullptr;
 }
 
 #ifdef HAVE_MC
 static char* MC_record_stack_to_string_liveness(xbt_fifo_t stack)
 {
   char* buffer;
-  size_t size;
-  FILE* file = open_memstream(&buffer, &size);
+  std::size_t size;
+  std::FILE* file = open_memstream(&buffer, &size);
 
   xbt_fifo_item_t item;
   xbt_fifo_item_t start = xbt_fifo_get_last_item(stack);
@@ -110,13 +111,13 @@ static char* MC_record_stack_to_string_liveness(xbt_fifo_t stack)
       // Serialization the (pid, value) pair:
       const char* sep = (item!=start) ? ";" : "";
       if (value)
-        fprintf(file, "%s%u/%u", sep, pid, value);
+        std::fprintf(file, "%s%u/%u", sep, pid, value);
       else
-        fprintf(file, "%s%u", sep, pid);
+        std::fprintf(file, "%s%u", sep, pid);
     }
   }
 
-  fclose(file);
+  std::fclose(file);
   return buffer;
 }
 
@@ -134,8 +135,8 @@ char* MC_record_stack_to_string(xbt_fifo_t stack)
   }
 
   char* buffer;
-  size_t size;
-  FILE* file = open_memstream(&buffer, &size);
+  std::size_t size;
+  std::FILE* file = open_memstream(&buffer, &size);
 
   xbt_fifo_item_t item;
   for (item = start; item; item = xbt_fifo_get_prev_item(item)) {
@@ -150,12 +151,12 @@ char* MC_record_stack_to_string(xbt_fifo_t stack)
     // Serialization the (pid, value) pair:
     const char* sep = (item!=start) ? ";" : "";
     if (value)
-      fprintf(file, "%s%u/%u", sep, pid, value);
+      std::fprintf(file, "%s%u/%u", sep, pid, value);
     else
-      fprintf(file, "%s%u", sep, pid);
+      std::fprintf(file, "%s%u", sep, pid);
   }
 
-  fclose(file);
+  std::fclose(file);
   return buffer;
 }
 
@@ -164,7 +165,7 @@ void MC_record_dump_path(xbt_fifo_t stack)
   if (MC_record_is_active()) {
     char* path = MC_record_stack_to_string(stack);
     XBT_INFO("Path = %s", path);
-    free(path);
+    std::free(path);
   }
 }
 #endif
index d6e5d54..2939b6a 100644 (file)
@@ -47,7 +47,7 @@ typedef struct s_mc_record_item {
 
 /** Convert a string representation of the path into a array of `s_mc_record_item_t`
  */
-XBT_INTERNAL xbt_dynar_t MC_record_from_string(const char* data);
+XBT_PRIVATE xbt_dynar_t MC_record_from_string(const char* data);
 
 /** Generate a string representation
 *
@@ -55,11 +55,11 @@ XBT_INTERNAL xbt_dynar_t MC_record_from_string(const char* data);
 * "pid0,value0;pid2,value2;pid3,value3". The value can be
 * omitted is it is null.
 */
-XBT_INTERNAL char* MC_record_stack_to_string(xbt_fifo_t stack);
+XBT_PRIVATE char* MC_record_stack_to_string(xbt_fifo_t stack);
 
 /** Dump the path represented by a given stack in the log
  */
-XBT_INTERNAL void MC_record_dump_path(xbt_fifo_t stack);
+XBT_PRIVATE void MC_record_dump_path(xbt_fifo_t stack);
 
 // ***** Replay
 
@@ -68,15 +68,15 @@ XBT_INTERNAL void MC_record_dump_path(xbt_fifo_t stack);
  *  \param start Array of record item
  *  \item  count Number of record items
  */
-XBT_INTERNAL void MC_record_replay(mc_record_item_t start, size_t count);
+XBT_PRIVATE void MC_record_replay(mc_record_item_t start, size_t count);
 
 /** Replay a path represented by a string
  *
  *  \param data String representation of the path
  */
-XBT_INTERNAL void MC_record_replay_from_string(const char* data);
+XBT_PRIVATE void MC_record_replay_from_string(const char* data);
 
-XBT_INTERNAL void MC_record_replay_init(void);
+XBT_PRIVATE void MC_record_replay_init(void);
 
 SG_END_DECL()
 
index 4503597..9791660 100644 (file)
@@ -401,12 +401,20 @@ char *MC_request_to_string(smx_simcall_t req, int value, e_mc_request_type_t req
     }
     break;
 
+  case SIMCALL_MUTEX_TRYLOCK:
   case SIMCALL_MUTEX_LOCK: {
-    type = "Mutex LOCK";
+    if (req->call == SIMCALL_MUTEX_LOCK)
+      type = "Mutex LOCK";
+    else
+      type = "Mutex TRYLOCK";
 
     s_smx_mutex_t mutex;
     mc_model_checker->process().read_bytes(&mutex, sizeof(mutex),
-      remote(simcall_mutex_lock__get__mutex(req)));
+      remote(
+        req->call == SIMCALL_MUTEX_LOCK
+        ? simcall_mutex_lock__get__mutex(req)
+        : simcall_mutex_trylock__get__mutex(req)
+      ));
     s_xbt_swag_t mutex_sleeping;
     mc_model_checker->process().read_bytes(&mutex_sleeping, sizeof(mutex_sleeping),
       remote(mutex.sleeping));
@@ -649,6 +657,10 @@ char *MC_request_get_dot_output(smx_simcall_t req, int value)
     }
     break;
 
+  case SIMCALL_MUTEX_TRYLOCK:
+    label = bprintf("[(%lu)] Mutex TRYLOCK", issuer->pid);
+    break;
+
   case SIMCALL_MUTEX_LOCK:
     label = bprintf("[(%lu)] Mutex LOCK", issuer->pid);
     break;
index 05bc77a..61062bc 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef SIMGRID_MC_REQUEST_H
 #define SIMGRID_MC_REQUEST_H
 
+#include <xbt/base.h>
+
 #include <simgrid_config.h>
 
 #include "../simix/smx_private.h"
@@ -19,11 +21,11 @@ typedef enum e_mc_request_type {
   MC_REQUEST_INTERNAL,
 } e_mc_request_type_t;
 
-XBT_INTERNAL int MC_request_depend(smx_simcall_t req1, smx_simcall_t req2);
-XBT_INTERNAL char* MC_request_to_string(smx_simcall_t req, int value, e_mc_request_type_t type);
-XBT_INTERNAL unsigned int MC_request_testany_fail(smx_simcall_t req);
-/*int MC_waitany_is_enabled_by_comm(smx_req_t req, unsigned int comm);*/
-XBT_INTERNAL int MC_request_is_visible(smx_simcall_t req);
+XBT_PRIVATE int MC_request_depend(smx_simcall_t req1, smx_simcall_t req2);
+XBT_PRIVATE char* MC_request_to_string(smx_simcall_t req, int value, e_mc_request_type_t type);
+XBT_PRIVATE unsigned int MC_request_testany_fail(smx_simcall_t req);
+/* XBT_PRIVATE int MC_waitany_is_enabled_by_comm(smx_req_t req, unsigned int comm);*/
+XBT_PRIVATE int MC_request_is_visible(smx_simcall_t req);
 
 /** Can this requests can be executed.
  *
@@ -32,16 +34,16 @@ XBT_INTERNAL int MC_request_is_visible(smx_simcall_t req);
  *  have both a source and a destination yet is not enabled
  *  (unless timeout is enabled in the wait and enabeld in SimGridMC).
  */
-XBT_INTERNAL int MC_request_is_enabled(smx_simcall_t req);
-XBT_INTERNAL int MC_request_is_enabled_by_idx(smx_simcall_t req, unsigned int idx);
+XBT_PRIVATE int MC_request_is_enabled(smx_simcall_t req);
+XBT_PRIVATE int MC_request_is_enabled_by_idx(smx_simcall_t req, unsigned int idx);
 
 /** Is the process ready to execute its simcall?
  *
  *  This is true if the request associated with the process is ready.
  */
-XBT_INTERNAL int MC_process_is_enabled(smx_process_t process);
+XBT_PRIVATE int MC_process_is_enabled(smx_process_t process);
 
-XBT_INTERNAL char *MC_request_get_dot_output(smx_simcall_t req, int value);
+XBT_PRIVATE char *MC_request_get_dot_output(smx_simcall_t req, int value);
 
 SG_END_DECL()
 
index 2ca64ec..65f381a 100644 (file)
@@ -199,6 +199,9 @@ void MC_modelcheck_safety(void)
       while ((state = (mc_state_t) xbt_fifo_shift(mc_stack))) {
         if (mc_reduce_kind == e_mc_reduce_dpor) {
           req = MC_state_get_internal_request(state);
+          if (req->call == SIMCALL_MUTEX_LOCK || req->call == SIMCALL_MUTEX_TRYLOCK)
+            xbt_die("Mutex is currently not supported with DPOR, "
+              "use --cfg=model-check/reduction:none");
           const smx_process_t issuer = MC_smx_simcall_get_issuer(req);
           xbt_fifo_foreach(mc_stack, item, prev_state, mc_state_t) {
             if (MC_request_depend(req, MC_state_get_internal_request(prev_state))) {
index 90bc4e0..14bcd4f 100644 (file)
@@ -10,6 +10,7 @@
 #include <stdint.h>
 
 #include <simgrid_config.h>
+#include <xbt/base.h>
 #include <xbt/dict.h>
 #include "mc_forward.hpp"
 #include "mc_state.h"
@@ -22,11 +23,11 @@ typedef enum {
   e_mc_reduce_dpor
 } e_mc_reduce_t;
 
-extern XBT_INTERNAL e_mc_reduce_t mc_reduce_kind;
+extern XBT_PRIVATE e_mc_reduce_t mc_reduce_kind;
 
 void MC_modelcheck_safety(void);
 
-typedef struct s_mc_visited_state{
+typedef struct XBT_PRIVATE s_mc_visited_state{
   mc_snapshot_t system_state;
   size_t heap_bytes_used;
   int nb_processes;
@@ -34,10 +35,10 @@ typedef struct s_mc_visited_state{
   int other_num; // dot_output for
 }s_mc_visited_state_t, *mc_visited_state_t;
 
-extern XBT_INTERNAL xbt_dynar_t visited_states;
-XBT_INTERNAL mc_visited_state_t is_visited_state(mc_state_t graph_state);
-XBT_INTERNAL void visited_state_free(mc_visited_state_t state);
-XBT_INTERNAL void visited_state_free_voidp(void *s);
+extern XBT_PRIVATE xbt_dynar_t visited_states;
+XBT_PRIVATE mc_visited_state_t is_visited_state(mc_state_t graph_state);
+XBT_PRIVATE void visited_state_free(mc_visited_state_t state);
+XBT_PRIVATE void visited_state_free_voidp(void *s);
 
 SG_END_DECL()
 
index 7a54ecc..f5457e1 100644 (file)
@@ -9,15 +9,15 @@
 
 #include <poll.h>
 
-#include <stdint.h>
 #include <stdbool.h>
 
 #include <sys/signalfd.h>
 #include <sys/types.h>
 
 #include <xbt/misc.h>
+#include <xbt/base.h>
  
-#include "mc_process.h"
+#include "mc/Process.hpp"
 #include "mc_exit.h"
 
 SG_BEGIN_DECL()
@@ -28,10 +28,10 @@ typedef struct s_mc_server s_mc_server_t, *mc_server_t;
 
 extern mc_server_t mc_server;
 
-XBT_INTERNAL void MC_server_wait_client(simgrid::mc::Process* process);
-XBT_INTERNAL void MC_server_simcall_handle(simgrid::mc::Process* process, unsigned long pid, int value);
+XBT_PRIVATE void MC_server_wait_client(simgrid::mc::Process* process);
+XBT_PRIVATE void MC_server_simcall_handle(simgrid::mc::Process* process, unsigned long pid, int value);
 
-XBT_INTERNAL void MC_server_loop(mc_server_t server);
+XBT_PRIVATE void MC_server_loop(mc_server_t server);
 
 SG_END_DECL()
 
index 643726e..7ef07f5 100644 (file)
@@ -87,7 +87,6 @@ static void MC_process_refresh_simix_process_list(
 void MC_process_smx_refresh(simgrid::mc::Process* process)
 {
   xbt_assert(mc_mode == MC_MODE_SERVER);
-  xbt_assert(!process->is_self());
   if (process->cache_flags & MC_PROCESS_CACHE_FLAG_SIMIX_PROCESSES)
     return;
 
@@ -212,6 +211,7 @@ const char* MC_smx_process_get_name(smx_process_t p)
   return info->name;
 }
 
+#ifdef HAVE_SMPI
 int MC_smpi_process_count(void)
 {
   if (mc_mode == MC_MODE_CLIENT)
@@ -223,6 +223,7 @@ int MC_smpi_process_count(void)
     return res;
   }
 }
+#endif
 
 unsigned long MC_smx_get_maxpid(void)
 {
index c9cdd7a..827634d 100644 (file)
@@ -14,7 +14,7 @@
 
 #include "smpi/private.h"
 
-#include "mc_process.h"
+#include "mc/Process.hpp"
 #include "mc_protocol.h"
 
 /** @file
@@ -49,9 +49,11 @@ struct s_mc_smx_process_info {
   char* name;
 };
 
-XBT_INTERNAL xbt_dynar_t MC_smx_process_info_list_new(void);
+typedef struct s_mc_smx_process_info s_mc_smx_process_info_t, *mc_smx_process_info_t;
 
-XBT_INTERNAL void MC_process_smx_refresh(simgrid::mc::Process* process);
+XBT_PRIVATE xbt_dynar_t MC_smx_process_info_list_new(void);
+
+XBT_PRIVATE void MC_process_smx_refresh(simgrid::mc::Process* process);
 
 /** Get the issuer of  a simcall (`req->issuer`)
  *
@@ -62,10 +64,10 @@ XBT_INTERNAL void MC_process_smx_refresh(simgrid::mc::Process* process);
  *  @param process the MCed process
  *  @param req     the simcall (copied in the local process)
  */
-XBT_INTERNAL smx_process_t MC_smx_simcall_get_issuer(smx_simcall_t req);
+XBT_PRIVATE smx_process_t MC_smx_simcall_get_issuer(smx_simcall_t req);
 
-XBT_INTERNAL const char* MC_smx_process_get_name(smx_process_t p);
-XBT_INTERNAL const char* MC_smx_process_get_host_name(smx_process_t p);
+XBT_PRIVATE const char* MC_smx_process_get_name(smx_process_t p);
+XBT_PRIVATE const char* MC_smx_process_get_host_name(smx_process_t p);
 
 #define MC_EACH_SIMIX_PROCESS(process, code) \
   if (mc_mode == MC_MODE_CLIENT) { \
@@ -83,20 +85,20 @@ XBT_INTERNAL const char* MC_smx_process_get_host_name(smx_process_t p);
   }
 
 /** Execute a given simcall */
-XBT_INTERNAL void MC_simcall_handle(smx_simcall_t req, int value);
+XBT_PRIVATE void MC_simcall_handle(smx_simcall_t req, int value);
 
-XBT_INTERNAL int MC_smpi_process_count(void);
+XBT_PRIVATE int MC_smpi_process_count(void);
 
 
 /* ***** Resolve (local/MCer structure from remote/MCed addresses) ***** */
 
 /** Get a local copy of the process from the process remote address */
-XBT_INTERNAL smx_process_t MC_smx_resolve_process(smx_process_t process_remote_address);
+XBT_PRIVATE smx_process_t MC_smx_resolve_process(smx_process_t process_remote_address);
 
 /** Get the process info structure from the process remote address */
-XBT_INTERNAL mc_smx_process_info_t MC_smx_resolve_process_info(smx_process_t process_remote_address);
+XBT_PRIVATE mc_smx_process_info_t MC_smx_resolve_process_info(smx_process_t process_remote_address);
 
-XBT_INTERNAL unsigned long MC_smx_get_maxpid(void);
+XBT_PRIVATE unsigned long MC_smx_get_maxpid(void);
 
 SG_END_DECL()
 
index 3aabd13..324c6ea 100644 (file)
@@ -153,8 +153,8 @@ int MC_snapshot_memcmp(
 namespace simgrid {
 namespace mc {
 
-Snapshot::Snapshot() :
-  process(nullptr),
+Snapshot::Snapshot(Process* process) :
+  AddressSpace(process),
   num_state(0),
   heap_bytes_used(0),
   enabled_processes(),
@@ -243,12 +243,12 @@ static void test_snapshot(bool sparse_checkpoint) {
     // Init memory and take snapshots:
     init_memory(source, byte_size);
     simgrid::mc::RegionSnapshot region0 = simgrid::mc::sparse_region(
-      simgrid::mc::RegionType::Unknown, source, source, byte_size);
+      simgrid::mc::RegionType::Unknown, source, source, byte_size, nullptr);
     for(int i=0; i<n; i+=2) {
       init_memory((char*) source + i*xbt_pagesize, xbt_pagesize);
     }
     simgrid::mc::RegionSnapshot region = simgrid::mc::sparse_region(
-      simgrid::mc::RegionType::Unknown, source, source, byte_size);
+      simgrid::mc::RegionType::Unknown, source, source, byte_size, nullptr);
 
     void* destination = mmap(NULL, byte_size, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
     xbt_assert(source!=MAP_FAILED, "Could not allocate destination memory");
@@ -283,7 +283,7 @@ static void test_snapshot(bool sparse_checkpoint) {
       xbt_test_add("Read pointer for %i page(s)", n);
       memcpy(source, &mc_model_checker, sizeof(void*));
       simgrid::mc::RegionSnapshot region2 = simgrid::mc::sparse_region(
-        simgrid::mc::RegionType::Unknown, source, source, byte_size);
+        simgrid::mc::RegionType::Unknown, source, source, byte_size, nullptr);
       xbt_test_assert(MC_region_read_pointer(&region2, source) == mc_model_checker,
         "Mismtach in MC_region_read_pointer()");
     }
index 183289e..cf2dc5a 100644 (file)
@@ -18,6 +18,7 @@
 #include "../xbt/mmalloc/mmprivate.h"
 #include <xbt/asserts.h>
 #include <xbt/dynar.h>
+#include <xbt/base.h>
 
 #include "mc_forward.hpp"
 #include "ModelChecker.hpp"
@@ -31,7 +32,7 @@ SG_BEGIN_DECL()
 
 // ***** Snapshot region
 
-XBT_INTERNAL void mc_region_restore_sparse(simgrid::mc::Process* process, mc_mem_region_t reg);
+XBT_PRIVATE void mc_region_restore_sparse(simgrid::mc::Process* process, mc_mem_region_t reg);
 
 static inline __attribute__((always_inline))
 void* mc_translate_address_region_chunked(uintptr_t addr, mc_mem_region_t region)
@@ -53,7 +54,7 @@ void* mc_translate_address_region(uintptr_t addr, mc_mem_region_t region, int pr
   case simgrid::mc::StorageType::Flat:
     {
       uintptr_t offset = (uintptr_t) addr - (uintptr_t) region->start().address();
-      return (void *) ((uintptr_t) region->flat_data().data() + offset);
+      return (void *) ((uintptr_t) region->flat_data() + offset);
     }
 
   case simgrid::mc::StorageType::Chunked:
@@ -71,7 +72,7 @@ void* mc_translate_address_region(uintptr_t addr, mc_mem_region_t region, int pr
   }
 }
 
-XBT_INTERNAL mc_mem_region_t mc_get_snapshot_region(
+XBT_PRIVATE mc_mem_region_t mc_get_snapshot_region(
   const void* addr, const simgrid::mc::Snapshot *snapshot, int process_index);
 
 }
@@ -118,7 +119,7 @@ typedef struct s_local_variable{
   int region;
 } s_local_variable_t, *local_variable_t;
 
-typedef struct s_mc_snapshot_stack {
+typedef struct XBT_PRIVATE s_mc_snapshot_stack {
   std::vector<s_local_variable> local_variables;
   s_mc_unw_context_t context;
   std::vector<s_mc_stack_frame_t> stack_frames;
@@ -139,15 +140,14 @@ typedef struct s_mc_global_t {
 namespace simgrid {
 namespace mc {
 
-class Snapshot : public AddressSpace {
+class XBT_PRIVATE Snapshot final : public AddressSpace {
 public:
-  Snapshot();
+  Snapshot(Process* process);
   ~Snapshot();
   const void* read_bytes(void* buffer, std::size_t size,
     remote_ptr<void> address, int process_index = ProcessIndexAny,
     ReadMode mode = Normal) const override;
 public: // To be private
-  simgrid::mc::Process* process;
   int num_state;
   size_t heap_bytes_used;
   std::vector<std::unique_ptr<s_mc_mem_region_t>> snapshot_regions;
@@ -177,20 +177,20 @@ mc_mem_region_t mc_get_region_hinted(void* addr, mc_snapshot_t snapshot, int pro
 
 static const void* mc_snapshot_get_heap_end(mc_snapshot_t snapshot);
 
-XBT_INTERNAL mc_snapshot_t MC_take_snapshot(int num_state);
-XBT_INTERNAL void MC_restore_snapshot(mc_snapshot_t);
+XBT_PRIVATE mc_snapshot_t MC_take_snapshot(int num_state);
+XBT_PRIVATE void MC_restore_snapshot(mc_snapshot_t);
 
-XBT_INTERNAL void mc_restore_page_snapshot_region(
+XBT_PRIVATE void mc_restore_page_snapshot_region(
   simgrid::mc::Process* process,
   void* start_addr, simgrid::mc::PerPageCopy const& pagenos);
 
-MC_SHOULD_BE_INTERNAL const void* MC_region_read_fragmented(
+const void* MC_region_read_fragmented(
   mc_mem_region_t region, void* target, const void* addr, size_t size);
 
-MC_SHOULD_BE_INTERNAL int MC_snapshot_region_memcmp(
+int MC_snapshot_region_memcmp(
   const void* addr1, mc_mem_region_t region1,
   const void* addr2, mc_mem_region_t region2, size_t size);
-XBT_INTERNAL int MC_snapshot_memcmp(
+XBT_PRIVATE int MC_snapshot_memcmp(
   const void* addr1, mc_snapshot_t snapshot1,
   const void* addr2, mc_snapshot_t snapshot2, int process_index, size_t size);
 
@@ -226,7 +226,7 @@ const void* MC_region_read(mc_mem_region_t region, void* target, const void* add
     xbt_die("Storage type not supported");
 
   case simgrid::mc::StorageType::Flat:
-    return (char*) region->flat_data().data() + offset;
+    return (char*) region->flat_data() + offset;
 
   case simgrid::mc::StorageType::Chunked:
     {
@@ -257,7 +257,7 @@ void* MC_region_read_pointer(mc_mem_region_t region, const void* addr)
 
 SG_END_DECL()
 
-XBT_INTERNAL int init_heap_information(xbt_mheap_t heap1, xbt_mheap_t heap2,
+XBT_PRIVATE int init_heap_information(xbt_mheap_t heap1, xbt_mheap_t heap2,
                           std::vector<s_mc_heap_ignore_region_t>* i1,
                           std::vector<s_mc_heap_ignore_region_t>* i2);
 
index 13c289d..fd14dc3 100644 (file)
@@ -7,13 +7,15 @@
 #ifndef SIMGRID_MC_STATE_H
 #define SIMGRID_MC_STATE_H
 
+#include <xbt/base.h>
+
 #include <simgrid_config.h>
 #include "../simix/smx_private.h"
 #include "mc_snapshot.h"
 
 SG_BEGIN_DECL()
 
-extern XBT_INTERNAL mc_global_t initial_global_state;
+extern XBT_PRIVATE mc_global_t initial_global_state;
 
 /* Possible exploration status of a process in a state */
 typedef enum {
@@ -36,7 +38,7 @@ typedef struct mc_procstate{
  *  For example WAITANY is transformes into a WAIT and TESTANY into TEST.
  *  See `MC_state_set_executed_request()`.
  */
-typedef struct mc_state {
+typedef struct XBT_PRIVATE mc_state {
   unsigned long max_pid;            /* Maximum pid at state's creation time */
   mc_procstate_t proc_status;       /* State's exploration status by process */
   s_smx_synchro_t internal_comm;     /* To be referenced by the internal_req */
@@ -52,16 +54,16 @@ typedef struct mc_state {
   xbt_dynar_t index_comm; // comm determinism verification
 } s_mc_state_t, *mc_state_t;
 
-XBT_INTERNAL mc_state_t MC_state_new(void);
-XBT_INTERNAL void MC_state_delete(mc_state_t state, int free_snapshot);
-XBT_INTERNAL void MC_state_interleave_process(mc_state_t state, smx_process_t process);
-XBT_INTERNAL unsigned int MC_state_interleave_size(mc_state_t state);
-XBT_INTERNAL int MC_state_process_is_done(mc_state_t state, smx_process_t process);
-XBT_INTERNAL void MC_state_set_executed_request(mc_state_t state, smx_simcall_t req, int value);
-XBT_INTERNAL smx_simcall_t MC_state_get_executed_request(mc_state_t state, int *value);
-XBT_INTERNAL smx_simcall_t MC_state_get_internal_request(mc_state_t state);
-XBT_INTERNAL smx_simcall_t MC_state_get_request(mc_state_t state, int *value);
-XBT_INTERNAL void MC_state_remove_interleave_process(mc_state_t state, smx_process_t process);
+XBT_PRIVATE mc_state_t MC_state_new(void);
+XBT_PRIVATE void MC_state_delete(mc_state_t state, int free_snapshot);
+XBT_PRIVATE void MC_state_interleave_process(mc_state_t state, smx_process_t process);
+XBT_PRIVATE unsigned int MC_state_interleave_size(mc_state_t state);
+XBT_PRIVATE int MC_state_process_is_done(mc_state_t state, smx_process_t process);
+XBT_PRIVATE void MC_state_set_executed_request(mc_state_t state, smx_simcall_t req, int value);
+XBT_PRIVATE smx_simcall_t MC_state_get_executed_request(mc_state_t state, int *value);
+XBT_PRIVATE smx_simcall_t MC_state_get_internal_request(mc_state_t state);
+XBT_PRIVATE smx_simcall_t MC_state_get_request(mc_state_t state, int *value);
+XBT_PRIVATE void MC_state_remove_interleave_process(mc_state_t state, smx_process_t process);
 
 SG_END_DECL()
 
index 899b403..c537850 100644 (file)
@@ -19,7 +19,7 @@
 #include <libunwind.h>
 
 #include "mc_object_info.h"
-#include "mc_process.h"
+#include "mc/Process.hpp"
 #include "mc_unw.h"
 #include "mc/Frame.hpp"
 
@@ -224,12 +224,6 @@ int mc_unw_init_cursor(unw_cursor_t *cursor, mc_unw_context_t context)
 {
   if (!context->process || !context->address_space)
     return -UNW_EUNSPEC;
-  simgrid::mc::AddressSpace* as = context->address_space;
-
-  simgrid::mc::Process* process = dynamic_cast<simgrid::mc::Process*>(as);
-  if (process && process->is_self())
-    return unw_init_local(cursor, &context->context);
-
   return unw_init_remote(cursor, context->process->unw_addr_space, context);
 }
 
index 9f85f72..915c445 100644 (file)
@@ -26,7 +26,9 @@
  *  much here.
  */
 
-#include "mc_process.h"
+#include <xbt/base.h>
+
+#include "mc/Process.hpp"
 
 SG_BEGIN_DECL()
 
@@ -43,7 +45,7 @@ SG_BEGIN_DECL()
  *
  *  It works with `void*` contexts allocated with `_UPT_create(pid)`.
  */
-extern unw_accessors_t mc_unw_vmread_accessors;
+extern XBT_PRIVATE unw_accessors_t mc_unw_vmread_accessors;
 
 /** Virtual table for our `libunwind` implementation
  *
@@ -52,26 +54,26 @@ extern unw_accessors_t mc_unw_vmread_accessors;
  *
  *  It works with the `s_mc_unw_context_t` context.
  */
-extern XBT_INTERNAL unw_accessors_t mc_unw_accessors;
+extern XBT_PRIVATE unw_accessors_t mc_unw_accessors;
 
 // ***** Libunwind context
 
 /** A `libunwind` context
  */
-typedef struct s_mc_unw_context {
+typedef struct XBT_PRIVATE s_mc_unw_context {
   simgrid::mc::AddressSpace* address_space;
   simgrid::mc::Process*       process;
   unw_context_t      context;
 } s_mc_unw_context_t, *mc_unw_context_t;
 
 /** Initialises an already allocated context */
-XBT_INTERNAL int mc_unw_init_context(
+XBT_PRIVATE int mc_unw_init_context(
   mc_unw_context_t context, simgrid::mc::Process* process, unw_context_t* c);
 
 // ***** Libunwind cursor
 
 /** Initialises a `libunwind` cursor */
-XBT_INTERNAL int mc_unw_init_cursor(unw_cursor_t *cursor, mc_unw_context_t context);
+XBT_PRIVATE int mc_unw_init_cursor(unw_cursor_t *cursor, mc_unw_context_t context);
 
 SG_END_DECL()
 
index edcfcff..40db5aa 100644 (file)
@@ -11,7 +11,7 @@
 #include "mc_safety.h"
 #include "mc_liveness.h"
 #include "mc_private.h"
-#include "mc_process.h"
+#include "mc/Process.hpp"
 #include "mc_smx.h"
 
 extern "C" {
@@ -60,13 +60,9 @@ static mc_visited_state_t visited_state_new()
     process->get_heap()->heaplimit,
     process->get_malloc_info());
 
-  if (mc_model_checker->process().is_self()) {
-    new_state->nb_processes = xbt_swag_size(simix_global->process_list);
-  } else {
-    MC_process_smx_refresh(&mc_model_checker->process());
-    new_state->nb_processes = xbt_dynar_length(
-      mc_model_checker->process().smx_process_infos);
-  }
+  MC_process_smx_refresh(&mc_model_checker->process());
+  new_state->nb_processes = xbt_dynar_length(
+    mc_model_checker->process().smx_process_infos);
 
   new_state->system_state = MC_take_snapshot(mc_stats->expanded_states);
   new_state->num = mc_stats->expanded_states;
@@ -85,13 +81,11 @@ mc_visited_pair_t MC_visited_pair_new(int pair_num, xbt_automaton_state_t automa
   pair->heap_bytes_used = mmalloc_get_bytes_used_remote(
     process->get_heap()->heaplimit,
     process->get_malloc_info());
-  if (mc_model_checker->process().is_self()) {
-    pair->nb_processes = xbt_swag_size(simix_global->process_list);
-  } else {
-    MC_process_smx_refresh(&mc_model_checker->process());
-    pair->nb_processes = xbt_dynar_length(
-      mc_model_checker->process().smx_process_infos);
-  }
+
+  MC_process_smx_refresh(&mc_model_checker->process());
+  pair->nb_processes = xbt_dynar_length(
+    mc_model_checker->process().smx_process_infos);
+
   pair->automaton_state = automaton_state;
   pair->num = pair_num;
   pair->other_num = -1;
@@ -222,6 +216,45 @@ int get_search_interval(xbt_dynar_t list, void *ref, int *min, int *max)
   return cursor;
 }
 
+static
+void replace_state(
+  mc_visited_state_t state_test, mc_visited_state_t new_state, int cursor)
+{
+  if (state_test->other_num == -1)
+    new_state->other_num = state_test->num;
+  else
+    new_state->other_num = state_test->other_num;
+
+  if (dot_output == NULL)
+    XBT_DEBUG("State %d already visited ! (equal to state %d)",
+      new_state->num, state_test->num);
+  else
+    XBT_DEBUG(
+      "State %d already visited ! (equal to state %d (state %d in dot_output))",
+      new_state->num, state_test->num, new_state->other_num);
+
+  /* Replace the old state with the new one (with a bigger num)
+     (when the max number of visited states is reached,  the oldest
+     one is removed according to its number (= with the min number) */
+  xbt_dynar_remove_at(visited_states, cursor, NULL);
+  xbt_dynar_insert_at(visited_states, cursor, &new_state);
+  XBT_DEBUG("Replace visited state %d with the new visited state %d",
+    state_test->num, new_state->num);
+}
+
+static
+bool some_dommunications_are_not_finished()
+{
+  for (size_t current_process = 1; current_process < MC_smx_get_maxpid(); current_process++) {
+    xbt_dynar_t pattern = xbt_dynar_get_as(
+      incomplete_communications_pattern, current_process, xbt_dynar_t);
+    if (!xbt_dynar_is_empty(pattern)) {
+      XBT_DEBUG("Some communications are not finished, cannot stop the exploration ! State not visited.");
+      return true;
+    }
+  }
+  return false;
+}
 
 /**
  * \brief Checks whether a given state has already been visited by the algorithm.
@@ -233,22 +266,11 @@ mc_visited_state_t is_visited_state(mc_state_t graph_state)
   if (_sg_mc_visited == 0)
     return NULL;
 
-  int partial_comm = 0;
-
   /* If comm determinism verification, we cannot stop the exploration if some 
      communications are not finished (at least, data are transfered). These communications 
      are incomplete and they cannot be analyzed and compared with the initial pattern. */
-  if (_sg_mc_comms_determinism || _sg_mc_send_determinism) {
-    size_t current_process = 1;
-    while (current_process < MC_smx_get_maxpid()) {
-      if (!xbt_dynar_is_empty((xbt_dynar_t)xbt_dynar_get_as(incomplete_communications_pattern, current_process, xbt_dynar_t))){
-        XBT_DEBUG("Some communications are not finished, cannot stop the exploration ! State not visited.");
-        partial_comm = 1;
-        break;
-      }
-      current_process++;
-    }
-  }
+  int partial_comm = (_sg_mc_comms_determinism || _sg_mc_send_determinism) &&
+    some_dommunications_are_not_finished();
 
   mc_visited_state_t new_state = visited_state_new();
   graph_state->system_state = new_state->system_state;
@@ -263,9 +285,6 @@ mc_visited_state_t is_visited_state(mc_state_t graph_state)
   } else {
 
     int min = -1, max = -1, index;
-    //int res;
-    mc_visited_state_t state_test;
-    int cursor;
 
     index = get_search_interval(visited_states, new_state, &min, &max);
 
@@ -274,7 +293,7 @@ mc_visited_state_t is_visited_state(mc_state_t graph_state)
       // Parallell implementation
       /*res = xbt_parmap_mc_apply(parmap, snapshot_compare, xbt_dynar_get_ptr(visited_states, min), (max-min)+1, new_state);
          if(res != -1){
-         state_test = (mc_visited_state_t)xbt_dynar_get_as(visited_states, (min+res)-1, mc_visited_state_t);
+         mc_visited_state_t state_test = (mc_visited_state_t)xbt_dynar_get_as(visited_states, (min+res)-1, mc_visited_state_t);
          if(state_test->other_num == -1)
          new_state->other_num = state_test->num;
          else
@@ -291,28 +310,13 @@ mc_visited_state_t is_visited_state(mc_state_t graph_state)
       if (_sg_mc_safety || (!partial_comm
         && initial_global_state->initial_communications_pattern_done)) {
 
-        cursor = min;
+        int cursor = min;
         while (cursor <= max) {
-          state_test = (mc_visited_state_t) xbt_dynar_get_as(visited_states, cursor, mc_visited_state_t);
+          mc_visited_state_t state_test = (mc_visited_state_t) xbt_dynar_get_as(visited_states, cursor, mc_visited_state_t);
           if (snapshot_compare(state_test, new_state) == 0) {
             // The state has been visited:
 
-            if (state_test->other_num == -1)
-              new_state->other_num = state_test->num;
-            else
-              new_state->other_num = state_test->other_num;
-            if (dot_output == NULL)
-              XBT_DEBUG("State %d already visited ! (equal to state %d)", new_state->num, state_test->num);
-            else
-              XBT_DEBUG("State %d already visited ! (equal to state %d (state %d in dot_output))", new_state->num, state_test->num, new_state->other_num);
-
-            /* Replace the old state with the new one (with a bigger num) 
-               (when the max number of visited states is reached,  the oldest 
-               one is removed according to its number (= with the min number) */
-            xbt_dynar_remove_at(visited_states, cursor, NULL);
-            xbt_dynar_insert_at(visited_states, cursor, &new_state);
-            XBT_DEBUG("Replace visited state %d with the new visited state %d", state_test->num, new_state->num);
-
+            replace_state(state_test, new_state, cursor);
             return state_test;
           }
           cursor++;
@@ -325,7 +329,7 @@ mc_visited_state_t is_visited_state(mc_state_t graph_state)
     } else {
 
       // The state has not been visited: insert the state in the dynamic array.
-      state_test = (mc_visited_state_t) xbt_dynar_get_as(visited_states, index, mc_visited_state_t);
+      mc_visited_state_t state_test = (mc_visited_state_t) xbt_dynar_get_as(visited_states, index, mc_visited_state_t);
       if (state_test->nb_processes < new_state->nb_processes) {
         xbt_dynar_insert_at(visited_states, index + 1, &new_state);
       } else {
@@ -348,8 +352,11 @@ mc_visited_state_t is_visited_state(mc_state_t graph_state)
       int min2 = mc_stats->expanded_states;
       unsigned int cursor2 = 0;
       unsigned int index2 = 0;
+
+      mc_visited_state_t state_test;
       xbt_dynar_foreach(visited_states, cursor2, state_test){
-        if (state_test->num < min2) {
+        if (!mc_model_checker->is_important_snapshot(*state_test->system_state)
+            && state_test->num < min2) {
           index2 = cursor2;
           min2 = state_test->num;
         }
@@ -466,7 +473,8 @@ int is_visited_pair(mc_visited_pair_t visited_pair, mc_pair_t pair) {
       unsigned int cursor2 = 0;
       unsigned int index2 = 0;
       xbt_dynar_foreach(visited_pairs, cursor2, pair_test) {
-        if (pair_test->num < min2) {
+        if (!mc_model_checker->is_important_snapshot(*pair_test->graph_state->system_state)
+            && pair_test->num < min2) {
           index2 = cursor2;
           min2 = pair_test->num;
         }
index 5303195..b83fb5f 100644 (file)
@@ -7,14 +7,17 @@
 #ifndef SIMGRID_MC_XBT_HPP
 #define SIMGRID_MC_XBT_HPP
 
+#include <xbt/base.h>
+
 #include "mc/AddressSpace.hpp"
 
 namespace simgrid {
 namespace mc {
 
-void read_element(AddressSpace const& as,
+XBT_PRIVATE void read_element(AddressSpace const& as,
   void* local, remote_ptr<s_xbt_dynar_t> addr, size_t i, size_t len);
-std::size_t read_length(AddressSpace const& as, remote_ptr<s_xbt_dynar_t> addr);
+XBT_PRIVATE std::size_t read_length(
+  AddressSpace const& as, remote_ptr<s_xbt_dynar_t> addr);
 
 }
 }
index f1fc2a1..5b0b6c7 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "internal_config.h"
 #include "mc_object_info.h"
 #include "mc/mc_private.h"
@@ -24,20 +26,20 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mcer_ignore, mc,
 
 // ***** Ignore heap chunks
 
-extern xbt_dynar_t mc_heap_comparison_ignore;
+extern XBT_PRIVATE xbt_dynar_t mc_heap_comparison_ignore;
 
-void heap_ignore_region_free(mc_heap_ignore_region_t r)
+static void heap_ignore_region_free(mc_heap_ignore_region_t r)
 {
   xbt_free(r);
 }
 
-void heap_ignore_region_free_voidp(void *r)
+static void heap_ignore_region_free_voidp(void *r)
 {
   heap_ignore_region_free((mc_heap_ignore_region_t) * (void **) r);
 }
 
 
-void MC_heap_region_ignore_insert(mc_heap_ignore_region_t region)
+XBT_PRIVATE void MC_heap_region_ignore_insert(mc_heap_ignore_region_t region)
 {
   if (mc_heap_comparison_ignore == NULL) {
     mc_heap_comparison_ignore =
@@ -76,7 +78,7 @@ void MC_heap_region_ignore_insert(mc_heap_ignore_region_t region)
     xbt_dynar_insert_at(mc_heap_comparison_ignore, cursor, &region);
 }
 
-void MC_heap_region_ignore_remove(void *address, size_t size)
+XBT_PRIVATE void MC_heap_region_ignore_remove(void *address, size_t size)
 {
   unsigned int cursor = 0;
   int start = 0;
@@ -113,7 +115,7 @@ void MC_heap_region_ignore_remove(void *address, size_t size)
 
 // ***** Ignore global variables
 
-void MCer_ignore_global_variable(const char *name)
+XBT_PRIVATE void MCer_ignore_global_variable(const char *name)
 {
   simgrid::mc::Process* process = &mc_model_checker->process();
   xbt_assert(!process->object_infos.empty(), "MC subsystem not initialized");
@@ -126,7 +128,7 @@ void MCer_ignore_global_variable(const char *name)
     while (start <= end) {
       unsigned int cursor = (start + end) / 2;
       simgrid::mc::Variable* current_var = &info->global_variables[cursor];
-      int cmp = strcmp(current_var->name.c_str(), name);
+      int cmp = current_var->name.compare(name);
       if (cmp == 0) {
         info->global_variables.erase(
           info->global_variables.begin() + cursor);
@@ -202,7 +204,7 @@ static void mc_ignore_local_variable_in_scope(const char *var_name,
       int cursor = (start + end) / 2;
       simgrid::mc::Variable* current_var = &scope->variables[cursor];
 
-      int compare = strcmp(current_var->name.c_str(), var_name);
+      int compare = current_var->name.compare(var_name);
       if (compare == 0) {
         // Variable found, remove it:
         scope->variables.erase(scope->variables.begin() + cursor);
@@ -231,9 +233,9 @@ static void mc_ignore_local_variable_in_scope(const char *var_name,
   }
 }
 
-extern xbt_dynar_t stacks_areas;
+extern XBT_PRIVATE xbt_dynar_t stacks_areas;
 
-void MC_stack_area_add(stack_region_t stack_area)
+XBT_PRIVATE void MC_stack_area_add(stack_region_t stack_area)
 {
   if (stacks_areas == NULL)
     stacks_areas = xbt_dynar_new(sizeof(stack_region_t), NULL);
index a339ae4..d5f5529 100644 (file)
 #include <xbt/dynar.h>
 
 #include "mc/datatypes.h"
-#include "mc/mc_process.h"
+#include "mc/Process.hpp"
 
 #include "xbt/misc.h"           /* SG_BEGIN_DECL */
 
 SG_BEGIN_DECL();
 
-XBT_INTERNAL void MCer_ignore_global_variable(const char *var_name);
-XBT_INTERNAL void MC_heap_region_ignore_insert(mc_heap_ignore_region_t region);
-XBT_INTERNAL void MC_heap_region_ignore_remove(void *address, size_t size);
+XBT_PRIVATE void MCer_ignore_global_variable(const char *var_name);
+XBT_PRIVATE void MC_heap_region_ignore_insert(mc_heap_ignore_region_t region);
+XBT_PRIVATE void MC_heap_region_ignore_remove(void *address, size_t size);
 
 SG_END_DECL();
 
index de39ff0..f13f9af 100644 (file)
@@ -10,6 +10,8 @@
 
 #include <sys/types.h>
 
+#include <xbt/base.h>
+
 #include "mc_memory_map.h"
 #include "mc_private.h"
 
@@ -23,7 +25,7 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(mc_memory_map, mc,
 namespace simgrid {
 namespace mc {
 
-std::vector<VmMap> get_memory_map(pid_t pid)
+XBT_PRIVATE std::vector<VmMap> get_memory_map(pid_t pid)
 {
   /* Open the actual process's proc maps file and create the memory_map_t */
   /* to be returned. */
index afe4ba0..f56cc71 100644 (file)
@@ -68,6 +68,11 @@ static int do_child(int socket, char** argv)
   // Set environment:
   setenv(MC_ENV_VARIABLE, "1", 1);
 
+  // Disable lazy relocation in the model-ched process.
+  // We don't want the model-checked process to modify its .got.plt during
+  // snapshot.
+  setenv("LC_BIND_NOW", "1", 1);
+
   char buffer[64];
   res = std::snprintf(buffer, sizeof(buffer), "%i", socket);
   if ((size_t) res >= sizeof(buffer) || res == -1)
@@ -114,6 +119,8 @@ static char** argvdup(int argc, char** argv)
 
 int main(int argc, char** argv)
 {
+  _sg_do_model_check = 1;
+
   // We need to keep the original parameters in order to pass them to the
   // model-checked process:
   int argc_copy = argc;
@@ -124,25 +131,6 @@ int main(int argc, char** argv)
   if (argc < 2)
     xbt_die("Missing arguments.\n");
 
-  bool server_mode = true;
-  char* env = std::getenv("SIMGRID_MC_MODE");
-  if (env) {
-    if (std::strcmp(env, "server") == 0)
-      server_mode = true;
-    else if (std::strcmp(env, "standalone") == 0)
-      server_mode = false;
-    else
-      xbt_die("Unrecognised value for SIMGRID_MC_MODE (server/standalone)");
-  }
-
-  if (!server_mode) {
-    setenv(MC_ENV_VARIABLE, "1", 1);
-    execvp(argv[1], argv+1);
-
-    std::perror("simgrid-mc");
-    return 127;
-  }
-
   // Create a AF_LOCAL socketpair:
   int res;
 
index 7b0f6ee..fcafb21 100644 (file)
@@ -81,7 +81,7 @@ msg_error_t MSG_parallel_task_execute(msg_task_t task)
                                                        1.0, -1.0);
       XBT_DEBUG("Parallel execution action created: %p", simdata->compute);
     } else {
-      unsigned long affinity_mask = (unsigned long) xbt_dict_get_or_null_ext(simdata->affinity_mask_db, (char *) p_simdata->m_host, sizeof(msg_host_t));
+      unsigned long affinity_mask = (unsigned long)(uintptr_t) xbt_dict_get_or_null_ext(simdata->affinity_mask_db, (char *) p_simdata->m_host, sizeof(msg_host_t));
       XBT_DEBUG("execute %s@%s with affinity(0x%04lx)", MSG_task_get_name(task), MSG_host_get_name(p_simdata->m_host), affinity_mask);
 
       simdata->compute = simcall_process_execute(task->name,
index 31823c3..136a2ec 100644 (file)
@@ -54,6 +54,10 @@ msg_host_t __MSG_host_create(sg_host_t host) // FIXME: don't return our paramete
 
   priv->affinity_mask_db = xbt_dict_new_homogeneous(NULL);
 
+  priv->file_descriptor_table = xbt_dynar_new(sizeof(int), NULL);
+  for (int i=1023; i>=0;i--)
+    xbt_dynar_push_as(priv->file_descriptor_table, int, i);
+
   sg_host_msg_set(host,priv);
   
   return host;
@@ -153,7 +157,7 @@ void __MSG_host_priv_free(msg_host_priv_t priv)
     XBT_WARN("dp_objs: %u pending task?", size);
   xbt_dict_free(&priv->dp_objs);
   xbt_dict_free(&priv->affinity_mask_db);
-
+  xbt_dynar_free(&priv->file_descriptor_table);
 #ifdef MSG_USE_DEPRECATED
   free(priv->mailboxes);
 #endif
@@ -475,3 +479,15 @@ xbt_dict_t MSG_host_get_storage_content(msg_host_t host)
   xbt_dict_free(&storage_list);
   return contents;
 }
+
+int __MSG_host_get_file_descriptor_id(msg_host_t host){
+  msg_host_priv_t priv = sg_host_msg(host);
+  xbt_assert(!xbt_dynar_is_empty(priv->file_descriptor_table),
+    "Too much files are opened! Some have to be closed.");
+  return xbt_dynar_pop_as(priv->file_descriptor_table, int);
+}
+
+void __MSG_host_release_file_descriptor_id(msg_host_t host, int id){
+  msg_host_priv_t priv = sg_host_msg(host);
+  xbt_dynar_push_as(priv->file_descriptor_table, int, id);
+}
index ca3ed09..d762d71 100644 (file)
@@ -18,6 +18,7 @@ XBT_LOG_NEW_DEFAULT_SUBCATEGORY(msg_io, msg,
  *  \see #msg_file_t
  */
 
+
 /********************************* File **************************************/
 void __MSG_file_get_info(msg_file_t fd){
 
@@ -79,10 +80,11 @@ void MSG_file_dump (msg_file_t fd){
            "\t\tMount point: '%s'\n"
            "\t\tStorage Id: '%s'\n"
            "\t\tStorage Type: '%s'\n"
-           "\t\tContent Type: '%s'",
+           "\t\tContent Type: '%s'\n"
+           "\t\tFile Descriptor Id: %d",
            priv->fullpath, priv->size, priv->mount_point,
            priv->storageId, priv->storage_type,
-           priv->content_type);
+           priv->content_type, priv->desc_id);
 }
 
 /** \ingroup msg_file_management
@@ -195,11 +197,16 @@ msg_file_t MSG_file_open(const char* fullpath, void* data)
   priv->fullpath = xbt_strdup(fullpath);
   priv->simdata = xbt_new0(s_simdata_file_t,1);
   priv->simdata->smx_file = simcall_file_open(fullpath, MSG_host_self());
-  name = bprintf("%s:%i:%s",MSG_host_get_name(MSG_host_self()),MSG_process_self_PID(),fullpath);
+  priv->desc_id = __MSG_host_get_file_descriptor_id(MSG_host_self());
+
+  name = bprintf("%s:%s:%d", priv->fullpath, MSG_host_get_name(MSG_host_self()),
+                             priv->desc_id);
+
   xbt_lib_set(file_lib, name, MSG_FILE_LEVEL, priv);
   msg_file_t fd = (msg_file_t) xbt_lib_get_elm_or_null(file_lib, name);
   __MSG_file_get_info(fd);
   xbt_free(name);
+
   return fd;
 }
 
@@ -217,7 +224,9 @@ int MSG_file_close(msg_file_t fd)
     xbt_free(priv->data);
 
   int res = simcall_file_close(priv->simdata->smx_file, MSG_host_self());
-  name = bprintf("%s:%i:%s",MSG_host_get_name(MSG_host_self()),MSG_process_self_PID(),priv->fullpath);
+  name = bprintf("%s:%s:%d", priv->fullpath, MSG_host_get_name(MSG_host_self()),
+                             priv->desc_id);
+  __MSG_host_release_file_descriptor_id(MSG_host_self(), priv->desc_id);
   xbt_lib_unset(file_lib, name, MSG_FILE_LEVEL, 1);
   xbt_free(name);
   return res;
index 4f45066..7ac2c96 100644 (file)
@@ -7,6 +7,7 @@
 #ifndef MSG_MAILBOX_H
 #define MSG_MAILBOX_H
 
+#include <xbt/base.h>
 #include "xbt/fifo.h"
 #include "simgrid/simix.h"
 #include "simgrid/msg.h"
@@ -27,7 +28,7 @@ SG_BEGIN_DECL()
 XBT_PUBLIC(msg_mailbox_t)
     MSG_mailbox_new(const char *alias);
 
-void MSG_mailbox_free(void *mailbox);
+XBT_PRIVATE void MSG_mailbox_free(void *mailbox);
 
 /* \brief MSG_mailbox_free - release a mailbox from the memory.
  *
@@ -38,7 +39,7 @@ void MSG_mailbox_free(void *mailbox);
  *
  * \see      MSG_mailbox_destroy.
  */
-void MSG_mailbox_free(void *mailbox);
+XBT_PRIVATE void MSG_mailbox_free(void *mailbox);
 
 /* \brief MSG_mailbox_get_by_alias - get a mailbox from its alias.
  *
index 3740c6c..01bbea5 100644 (file)
@@ -10,6 +10,7 @@
 #include "simgrid/msg.h"
 #include "simgrid/simix.h"
 #include "surf/surf.h"
+#include "xbt/base.h"
 #include "xbt/fifo.h"
 #include "xbt/dynar.h"
 #include "xbt/swag.h"
@@ -66,6 +67,9 @@ typedef struct simdata_file {
   smx_file_t smx_file;
 } s_simdata_file_t;
 
+XBT_PRIVATE int __MSG_host_get_file_descriptor_id(msg_host_t host);
+XBT_PRIVATE void __MSG_host_release_file_descriptor_id(msg_host_t host, int id);
+
 /*************** Begin GPU ***************/
 typedef struct simdata_gpu_task {
   double flops_amount;    /* Computation size */
@@ -154,66 +158,66 @@ XBT_PUBLIC_DATA(MSG_Global_t) msg_global;
 #  define MSG_RETURN(val) return(val)
 #endif
 
-msg_host_t __MSG_host_create(sg_host_t host);
-msg_storage_t __MSG_storage_create(smx_storage_t storage);
+XBT_PRIVATE msg_host_t __MSG_host_create(sg_host_t host);
+XBT_PRIVATE msg_storage_t __MSG_storage_create(smx_storage_t storage);
 void __MSG_host_destroy(msg_host_t host);
-void __MSG_host_priv_free(msg_host_priv_t priv);
-void __MSG_storage_destroy(msg_storage_priv_t host);
-void __MSG_file_destroy(msg_file_priv_t host);
+XBT_PRIVATE void __MSG_host_priv_free(msg_host_priv_t priv);
+XBT_PRIVATE void __MSG_storage_destroy(msg_storage_priv_t host);
+XBT_PRIVATE void __MSG_file_destroy(msg_file_priv_t host);
 
-void MSG_process_cleanup_from_SIMIX(smx_process_t smx_proc);
-smx_process_t MSG_process_create_from_SIMIX(const char *name,
+XBT_PRIVATE void MSG_process_cleanup_from_SIMIX(smx_process_t smx_proc);
+XBT_PRIVATE smx_process_t MSG_process_create_from_SIMIX(const char *name,
                                    xbt_main_func_t code, void *data,
                                    const char *hostname, double kill_time,
                                    int argc, char **argv,
                                    xbt_dict_t properties, int auto_restart,
                                    smx_process_t parent_process);
-void MSG_comm_copy_data_from_SIMIX(smx_synchro_t comm, void* buff, size_t buff_size);
+XBT_PRIVATE void MSG_comm_copy_data_from_SIMIX(smx_synchro_t comm, void* buff, size_t buff_size);
 
-void MSG_post_create_environment(void);
+XBT_PRIVATE void MSG_post_create_environment(void);
 
-void MSG_host_add_task(msg_host_t host, msg_task_t task);
-void MSG_host_del_task(msg_host_t host, msg_task_t task);
+XBT_PRIVATE void MSG_host_add_task(msg_host_t host, msg_task_t task);
+XBT_PRIVATE void MSG_host_del_task(msg_host_t host, msg_task_t task);
 
 /********** Tracing **********/
 /* declaration of instrumentation functions from msg_task_instr.c */
-void TRACE_msg_set_task_category(msg_task_t task, const char *category);
-void TRACE_msg_task_create(msg_task_t task);
-void TRACE_msg_task_execute_start(msg_task_t task);
-void TRACE_msg_task_execute_end(msg_task_t task);
-void TRACE_msg_task_destroy(msg_task_t task);
-void TRACE_msg_task_get_start(void);
-void TRACE_msg_task_get_end(double start_time, msg_task_t task);
-int TRACE_msg_task_put_start(msg_task_t task);    //returns TRUE if the task_put_end must be called
-void TRACE_msg_task_put_end(void);
+XBT_PRIVATE void TRACE_msg_set_task_category(msg_task_t task, const char *category);
+XBT_PRIVATE void TRACE_msg_task_create(msg_task_t task);
+XBT_PRIVATE void TRACE_msg_task_execute_start(msg_task_t task);
+XBT_PRIVATE void TRACE_msg_task_execute_end(msg_task_t task);
+XBT_PRIVATE void TRACE_msg_task_destroy(msg_task_t task);
+XBT_PRIVATE void TRACE_msg_task_get_end(double start_time, msg_task_t task);
+XBT_PRIVATE void TRACE_msg_task_get_start(void);
+XBT_PRIVATE int TRACE_msg_task_put_start(msg_task_t task);    //returns TRUE if the task_put_end must be called
+XBT_PRIVATE void TRACE_msg_task_put_end(void);
 
 /* declaration of instrumentation functions from msg_process_instr.c */
-char *instr_process_id (msg_process_t proc, char *str, int len);
-char *instr_process_id_2 (const char *process_name, int process_pid, char *str, int len);
-void TRACE_msg_process_change_host(msg_process_t process, msg_host_t old_host,
+XBT_PRIVATE char *instr_process_id (msg_process_t proc, char *str, int len);
+XBT_PRIVATE char *instr_process_id_2 (const char *process_name, int process_pid, char *str, int len);
+XBT_PRIVATE void TRACE_msg_process_change_host(msg_process_t process, msg_host_t old_host,
                                    msg_host_t new_host);
-void TRACE_msg_process_create (const char *process_name, int process_pid, msg_host_t host);
-void TRACE_msg_process_destroy (const char *process_name, int process_pid, msg_host_t host);
-void TRACE_msg_process_kill(smx_process_exit_status_t status, msg_process_t process);
-void TRACE_msg_process_suspend(msg_process_t process);
-void TRACE_msg_process_resume(msg_process_t process);
-void TRACE_msg_process_sleep_in(msg_process_t process);   //called from msg/gos.c
-void TRACE_msg_process_sleep_out(msg_process_t process);
-void TRACE_msg_process_end(msg_process_t process);
+XBT_PRIVATE void TRACE_msg_process_create (const char *process_name, int process_pid, msg_host_t host);
+XBT_PRIVATE void TRACE_msg_process_destroy (const char *process_name, int process_pid, msg_host_t host);
+XBT_PRIVATE void TRACE_msg_process_kill(smx_process_exit_status_t status, msg_process_t process);
+XBT_PRIVATE void TRACE_msg_process_suspend(msg_process_t process);
+XBT_PRIVATE void TRACE_msg_process_resume(msg_process_t process);
+XBT_PRIVATE void TRACE_msg_process_sleep_in(msg_process_t process);   //called from msg/gos.c
+XBT_PRIVATE void TRACE_msg_process_sleep_out(msg_process_t process);
+XBT_PRIVATE void TRACE_msg_process_end(msg_process_t process);
 
 /* declaration of instrumentation functions from instr_msg_vm.c */
-char *instr_vm_id(msg_vm_t vm, char *str, int len);
-char *instr_vm_id_2(const char *vm_name, char *str, int len);
-void TRACE_msg_vm_change_host(msg_vm_t vm, msg_host_t old_host,
+XBT_PRIVATE char *instr_vm_id(msg_vm_t vm, char *str, int len);
+XBT_PRIVATE char *instr_vm_id_2(const char *vm_name, char *str, int len);
+XBT_PRIVATE void TRACE_msg_vm_change_host(msg_vm_t vm, msg_host_t old_host,
                                    msg_host_t new_host);
-void TRACE_msg_vm_start(msg_vm_t vm);
-void TRACE_msg_vm_create(const char *vm_name, msg_host_t host);
-void TRACE_msg_vm_kill(msg_vm_t process);
-void TRACE_msg_vm_suspend(msg_vm_t vm);
-void TRACE_msg_vm_resume(msg_vm_t vm);
-void TRACE_msg_vm_save(msg_vm_t vm);
-void TRACE_msg_vm_restore(msg_vm_t vm);
-void TRACE_msg_vm_end(msg_vm_t vm);
+XBT_PRIVATE void TRACE_msg_vm_start(msg_vm_t vm);
+XBT_PRIVATE void TRACE_msg_vm_create(const char *vm_name, msg_host_t host);
+XBT_PRIVATE void TRACE_msg_vm_kill(msg_vm_t process);
+XBT_PRIVATE void TRACE_msg_vm_suspend(msg_vm_t vm);
+XBT_PRIVATE void TRACE_msg_vm_resume(msg_vm_t vm);
+XBT_PRIVATE void TRACE_msg_vm_save(msg_vm_t vm);
+XBT_PRIVATE void TRACE_msg_vm_restore(msg_vm_t vm);
+XBT_PRIVATE void TRACE_msg_vm_end(msg_vm_t vm);
 
 SG_END_DECL()
 #endif
index 5e78505..3db6204 100644 (file)
@@ -489,7 +489,7 @@ void MSG_task_set_affinity(msg_task_t task, msg_host_t host, unsigned long mask)
         xbt_dict_remove_ext(task->simdata->affinity_mask_db, (char *) host, sizeof(host));
     }
   } else
-    xbt_dict_set_ext(task->simdata->affinity_mask_db, (char *) host, sizeof(host), (void *) mask, NULL);
+    xbt_dict_set_ext(task->simdata->affinity_mask_db, (char *) host, sizeof(host), (void *)(uintptr_t) mask, NULL);
 
   /* We set affinity data of this task. If the task is being executed, we
    * actually change the affinity setting of the task. Otherwise, this change
@@ -513,7 +513,7 @@ void MSG_task_set_affinity(msg_task_t task, msg_host_t host, unsigned long mask)
     /* task is being executed on this host. so change the affinity now */
     {
       /* check it works. remove me if it works. */
-      xbt_assert((unsigned long) xbt_dict_get_or_null_ext(task->simdata->affinity_mask_db, (char *) host, sizeof(msg_host_t)) == mask);
+      xbt_assert((unsigned long)(uintptr_t) xbt_dict_get_or_null_ext(task->simdata->affinity_mask_db, (char *) host, sizeof(msg_host_t)) == mask);
     }
 
     XBT_INFO("set affinity(0x%04lx@%s) for %s", mask, MSG_host_get_name(host), MSG_task_get_name(task));
index a1df02d..dfb255c 100644 (file)
@@ -409,7 +409,7 @@ static int migration_rx_fun(int argc, char *argv[])
   /* install the affinity setting of the VM on the destination pm */
   {
 
-    unsigned long affinity_mask = (unsigned long) xbt_dict_get_or_null_ext(priv->affinity_mask_db, (char *)dst_pm, sizeof(msg_host_t));
+    unsigned long affinity_mask = (unsigned long)(uintptr_t) xbt_dict_get_or_null_ext(priv->affinity_mask_db, (char *)dst_pm, sizeof(msg_host_t));
     simcall_vm_set_affinity(vm, dst_pm, affinity_mask);
     XBT_DEBUG("set affinity(0x%04lx@%s) for %s", affinity_mask, MSG_host_get_name(dst_pm), MSG_host_get_name(vm));
   }
@@ -604,7 +604,7 @@ static sg_size_t send_migration_data(msg_vm_t vm, msg_host_t src_pm, msg_host_t
 {
   sg_size_t sent = 0;
   char *task_name = get_mig_task_name(vm, src_pm, dst_pm, stage);
-  msg_task_t task = MSG_task_create(task_name, 0, size, NULL);
+  msg_task_t task = MSG_task_create(task_name, 0, (double)size, NULL);
 
   /* TODO: clean up */
 
@@ -621,7 +621,7 @@ static sg_size_t send_migration_data(msg_vm_t vm, msg_host_t src_pm, msg_host_t
   if (ret == MSG_OK) {
     sent = size;
   } else if (ret == MSG_TIMEOUT) {
-    sg_size_t remaining = MSG_task_get_remaining_communication(task);
+    sg_size_t remaining = (sg_size_t)MSG_task_get_remaining_communication(task);
     sent = size - remaining;
     XBT_INFO("timeout (%lf s) in sending_migration_data, remaining %llu bytes of %llu",
         timeout, remaining, size);
@@ -714,7 +714,7 @@ static int migration_tx_fun(int argc, char *argv[])
 #define MIGRATION_TIMEOUT_DO_NOT_HARDCODE_ME 10000000.0
   double mig_timeout = MIGRATION_TIMEOUT_DO_NOT_HARDCODE_ME;
 
-  double remaining_size = ramsize + devsize;
+  double remaining_size = (double) (ramsize + devsize);
   double threshold = 0.0;
 
   /* check parameters */
@@ -851,7 +851,7 @@ stage3:
 
   TRY {
     XBT_DEBUG("Stage 3: Gonna send %f", remaining_size);
-    send_migration_data(ms->vm, ms->src_pm, ms->dst_pm, remaining_size, ms->mbox, 3, 0, mig_speed, -1);
+    send_migration_data(ms->vm, ms->src_pm, ms->dst_pm, (sg_size_t)remaining_size, ms->mbox, 3, 0, mig_speed, -1);
   } CATCH_ANONYMOUS {
     //hostfailure (if you want to know whether this is the SRC or the DST please check directly in send_migration_data code)
     // Stop the dirty page tracking an return (there is no memory space to release)
@@ -1115,7 +1115,7 @@ msg_host_t MSG_vm_get_pm(msg_vm_t vm)
  */
 void MSG_vm_set_bound(msg_vm_t vm, double bound)
 {
-  return simcall_vm_set_bound(vm, bound);
+  simcall_vm_set_bound(vm, bound);
 }
 
 
@@ -1132,7 +1132,7 @@ void MSG_vm_set_affinity(msg_vm_t vm, msg_host_t pm, unsigned long mask)
   if (mask == 0)
     xbt_dict_remove_ext(priv->affinity_mask_db, (char *) pm, sizeof(pm));
   else
-    xbt_dict_set_ext(priv->affinity_mask_db, (char *) pm, sizeof(pm), (void *) mask, NULL);
+    xbt_dict_set_ext(priv->affinity_mask_db, (char *) pm, sizeof(pm), (void *)(uintptr_t) mask, NULL);
 
   msg_host_t pm_now = MSG_vm_get_pm(vm);
   if (pm_now == pm) {
index cbc1c57..d3d435b 100644 (file)
 #define SIMGRID_PORTABLE_H
 
 #include "internal_config.h"
+#include "xbt/base.h"
 #include "xbt/misc.h"
-/* 
- * win32 or win64 (__XBT_WIN32 is defined for win32 and win64 applications, __TOS_WIN__ is defined by xlC).
-*/
 #ifdef _XBT_WIN32
-# include "win32/config.h"
 # include <windows.h>
 #endif
 
 
 #include <fcntl.h>
 
+#ifdef _XBT_WIN32
+  #ifndef EWOULDBLOCK
+  #define EWOULDBLOCK WSAEWOULDBLOCK
+  #endif
+
+  #ifndef EINPROGRESS
+  #define EINPROGRESS WSAEINPROGRESS
+  #endif
+
+  #ifndef ETIMEDOUT
+  #define ETIMEDOUT   WSAETIMEDOUT
+  #endif
+
+  #ifdef S_IRGRP
+    #undef S_IRGRP
+  #endif
+  #define S_IRGRP 0
+
+  #ifdef S_IWGRP
+    #undef S_IWGRP
+  #endif
+  #define S_IWGRP 0
+#endif
+
 #ifdef HAVE_SYS_STAT_H
 #  include <sys/stat.h>
 #endif
  **** Time handling
  ****/
 
-#ifdef TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
+#if HAVE_SYS_TIME_H
 #  include <sys/time.h>
-# else
-#  include <time.h>
-# endif
 #endif
+#include <time.h>
 
 /****
  **** Signals
@@ -89,9 +104,9 @@ XBT_PUBLIC(int) vsnprintf(char *, size_t, const char *, va_list);
 
 /* use internal functions when OS provided ones are borken */
 #if defined(HAVE_SNPRINTF) && defined(PREFER_PORTABLE_SNPRINTF)
-extern int portable_snprintf(char *str, size_t str_m, const char *fmt,
+XBT_PRIVATE int portable_snprintf(char *str, size_t str_m, const char *fmt,
                              /*args */ ...);
-extern int portable_vsnprintf(char *str, size_t str_m, const char *fmt,
+XBT_PRIVATE int portable_vsnprintf(char *str, size_t str_m, const char *fmt,
                               va_list ap);
 #define snprintf  portable_snprintf
 #define vsnprintf portable_vsnprintf
index b62dabe..c1191e1 100644 (file)
@@ -47,6 +47,8 @@
 #ifndef _FLEXML_dax_H
 #define _FLEXML_dax_H
 
+#include <xbt/base.h>
+
 /* XML application entry points. */
 XBT_PUBLIC(void) STag_dax__adag(void);
 XBT_PUBLIC(void) ETag_dax__adag(void);
@@ -194,5 +196,5 @@ XBT_PUBLIC(int) dax__element_context(int);
 XBT_PUBLIC(int) yylex(void);
 
 /* Flexml error handling function (useful only when -q flag passed to flexml) */
-const char * dax__parse_err_msg(void);
+XBT_PRIVATE const char * dax__parse_err_msg(void);
 #endif
index 8549aea..b99e992 100644 (file)
@@ -7,6 +7,7 @@
 #ifndef SIMDAG_PRIVATE_H
 #define SIMDAG_PRIVATE_H
 
+#include "xbt/base.h"
 #include "xbt/dict.h"
 #include "xbt/dynar.h"
 #include "xbt/fifo.h"
@@ -47,7 +48,7 @@ typedef struct SD_global {
 
 } s_SD_global_t, *SD_global_t;
 
-extern SD_global_t sd_global;
+extern XBT_PRIVATE SD_global_t sd_global;
 
 /* Workstation */
 typedef s_xbt_dictelm_t s_SD_workstation_t;
@@ -121,21 +122,21 @@ typedef struct SD_dependency {
 XBT_PUBLIC(xbt_swag_t) SD_simulate_swag(double how_long); /* could be public, but you need to see the internals of the SD_task_t to use it */
 
 
-SD_workstation_t __SD_workstation_create(void *surf_workstation,
+XBT_PRIVATE SD_workstation_t __SD_workstation_create(void *surf_workstation,
                                          void *data);
-void __SD_workstation_destroy(void *workstation);
-int __SD_workstation_is_busy(SD_workstation_t workstation);
+XBT_PRIVATE void __SD_workstation_destroy(void *workstation);
+XBT_PRIVATE int __SD_workstation_is_busy(SD_workstation_t workstation);
 
-void __SD_task_set_state(SD_task_t task, e_SD_task_state_t new_state);
-void __SD_task_really_run(SD_task_t task);
-int __SD_task_try_to_run(SD_task_t task);
-void __SD_task_just_done(SD_task_t task);
-bool acyclic_graph_detail(xbt_dynar_t dag);
+XBT_PRIVATE void __SD_task_set_state(SD_task_t task, e_SD_task_state_t new_state);
+XBT_PRIVATE void __SD_task_really_run(SD_task_t task);
+XBT_PRIVATE void __SD_task_just_done(SD_task_t task);
+XBT_PRIVATE int __SD_task_try_to_run(SD_task_t task);
+XBT_PRIVATE bool acyclic_graph_detail(xbt_dynar_t dag);
 
 /* Task mallocator functions */
-void* SD_task_new_f(void);
-void SD_task_recycle_f(void *t);
-void SD_task_free_f(void *t);
+XBT_PRIVATE void* SD_task_new_f(void);
+XBT_PRIVATE void SD_task_recycle_f(void *t);
+XBT_PRIVATE void SD_task_free_f(void *t);
 
 /* Functions to test if the task is in a given state. */
 
@@ -197,15 +198,15 @@ static XBT_INLINE int __SD_task_is_running(SD_task_t task)
 }
 
 /********** Storage **********/
-SD_storage_t __SD_storage_create(void *surf_storage, void *data);
-void __SD_storage_destroy(void *storage);
+XBT_PRIVATE SD_storage_t __SD_storage_create(void *surf_storage, void *data);
+XBT_PRIVATE void __SD_storage_destroy(void *storage);
 
 /********** Tracing **********/
 /* declaration of instrumentation functions from sd_task_instr.c */
-void TRACE_sd_task_create(SD_task_t task);
-void TRACE_sd_task_execute_start(SD_task_t task);
-void TRACE_sd_task_execute_end(SD_task_t task);
-void TRACE_sd_task_destroy(SD_task_t task);
+XBT_PRIVATE void TRACE_sd_task_create(SD_task_t task);
+XBT_PRIVATE void TRACE_sd_task_execute_start(SD_task_t task);
+XBT_PRIVATE void TRACE_sd_task_execute_end(SD_task_t task);
+XBT_PRIVATE void TRACE_sd_task_destroy(SD_task_t task);
 
 SG_END_DECL()
 
index e2873cd..5eefa8e 100644 (file)
@@ -8,7 +8,7 @@
 #include "simgrid/simdag.h"
 #include "xbt/misc.h"
 #include "xbt/log.h"
-#include <libgen.h>
+#include "xbt/file.h" /* xbt_basename() */
 
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(sd_daxparse, sd, "Parsing DAX files");
 
@@ -368,8 +368,8 @@ xbt_dynar_t SD_daxload(const char *filename)
   }
 
   if (!acyclic_graph_detail(result)){
-    XBT_ERROR("The DAX described in %s is not a DAG. It contains a cycle.",
-              basename((char*)filename));
+    XBT_ERROR("The DAX described in %s is not a DAG. It contains a cycle.", 
+             xbt_basename(filename));
     xbt_dynar_foreach(result, cpt, file)
       SD_task_destroy(file);
      xbt_dynar_free_container(&result);
@@ -381,7 +381,7 @@ xbt_dynar_t SD_daxload(const char *filename)
 
 void STag_dax__adag(void)
 {
-  _XBT_GNUC_UNUSED double version;
+  XBT_ATTRIB_UNUSED double version;
   version = dax_parse_double(A_dax__adag_version);
 
   xbt_assert(version == 2.1,
index b361678..2ce94c9 100644 (file)
@@ -18,7 +18,9 @@
 #include "instr/instr_interface.h"
 #include "simgrid/simix.h"
 #include "simgrid/sg_config.h"
+#ifdef HAVE_SMPI
 #include "smpi/smpi_interface.h"
+#endif
 #include "mc/mc.h"
 #include "mc/mc_record.h"
 #include "simgrid/instr.h"
@@ -377,17 +379,6 @@ static void _sg_cfg_cb_model_check_replay(const char *name, int pos)
   MC_record_path = xbt_cfg_get_string(_sg_cfg_set, name);
 }
 
-static void _sg_cfg_cb_model_check(const char *name, int pos)
-{
-#ifdef HAVE_MC
-  _sg_do_model_check = xbt_cfg_get_boolean(_sg_cfg_set, name);
-#else
-  if (xbt_cfg_get_boolean(_sg_cfg_set, name)) {
-    xbt_die("You tried to activate the model-checking from the command line, but it was not compiled in. Change your settings in cmake, recompile and try again");
-  }
-#endif
-}
-
 static void _sg_cfg_cb_model_check_record(const char *name, int pos)
 {
 #ifdef HAVE_MC
@@ -615,12 +606,6 @@ void sg_config_init(int *argc, char **argv)
       xbt_cfgelm_string, 0, 1, _sg_cfg_cb_model_check_replay, NULL);
 
 #ifdef HAVE_MC
-    /* do model-checking */
-    xbt_cfg_register(&_sg_cfg_set, "model-check",
-                     "Verify the system through model-checking instead of simulating it (EXPERIMENTAL)",
-                     xbt_cfgelm_boolean, 1, 1, _sg_cfg_cb_model_check, NULL);
-    xbt_cfg_setdefault_boolean(_sg_cfg_set, "model-check", "no");
-
     /* do model-checking-record */
     xbt_cfg_register(&_sg_cfg_set, "model-check/record",
                      "Record the model-checking paths",
@@ -640,6 +625,17 @@ void sg_config_init(int *argc, char **argv)
                      xbt_cfgelm_boolean, 1, 1, _mc_cfg_cb_sparse_checkpoint, NULL);
     xbt_cfg_setdefault_boolean(_sg_cfg_set, "model-check/sparse-checkpoint", "no");
 
+    /* do stateful model-checking */
+    xbt_cfg_register(&_sg_cfg_set, "model-check/soft-dirty",
+                     "Use sparse per-page snapshots.",
+                     xbt_cfgelm_boolean, 1, 1, _mc_cfg_cb_soft_dirty, NULL);
+    xbt_cfg_setdefault_boolean(_sg_cfg_set, "model-check/soft-dirty", "no");
+
+    xbt_cfg_register(&_sg_cfg_set, "model-check/ksm",
+                     "Kernel same-page merging",
+                     xbt_cfgelm_boolean, 1, 1, _mc_cfg_cb_ksm, NULL);
+    xbt_cfg_setdefault_boolean(_sg_cfg_set, "model-check/ksm", "no");
+
     /* do liveness model-checking */
     xbt_cfg_register(&_sg_cfg_set, "model-check/property",
                      "Specify the name of the file containing the property. It must be the result of the ltl2ba program.",
index 32ba9c4..1950707 100644 (file)
@@ -9,12 +9,14 @@
 
 #include <algorithm>
 
+#include <xbt/base.h>
+
 namespace simgrid {
 namespace util {
 
 /** Find a pointer to a value stores in a map (or nullptr) */
 template<typename C, typename K>
-inline
+inline XBT_PRIVATE
 typename C::mapped_type* find_map_ptr(C& c, K const& k)
 {
   typename C::iterator i = c.find(k);
@@ -25,7 +27,7 @@ typename C::mapped_type* find_map_ptr(C& c, K const& k)
 }
 
 template<typename C, typename K>
-inline
+inline XBT_PRIVATE
 typename C::mapped_type const* find_map_ptr(C const& c, K const& k)
 {
   typename C::const_iterator i = c.find(k);
index 75b3d05..951504c 100644 (file)
@@ -1942,61 +1942,61 @@ static inline void simcall_mc_compare_snapshots__set__result(smx_simcall_t simca
 
 /* The prototype of all simcall handlers, automatically generated for you */
 
-void simcall_HANDLER_host_off(smx_simcall_t simcall, sg_host_t host);
-void simcall_HANDLER_vm_suspend(smx_simcall_t simcall, sg_host_t ind_vm);
-void simcall_HANDLER_vm_resume(smx_simcall_t simcall, sg_host_t ind_vm);
-void simcall_HANDLER_vm_shutdown(smx_simcall_t simcall, sg_host_t ind_vm);
-void simcall_HANDLER_vm_save(smx_simcall_t simcall, sg_host_t ind_vm);
-void simcall_HANDLER_vm_restore(smx_simcall_t simcall, sg_host_t ind_vm);
-void* simcall_HANDLER_process_create(smx_simcall_t simcall, const char* name, xbt_main_func_t code, void* data, const char* hostname, double kill_time, int argc, char** argv, xbt_dict_t properties, int auto_restart);
-void simcall_HANDLER_process_kill(smx_simcall_t simcall, smx_process_t process);
-void simcall_HANDLER_process_killall(smx_simcall_t simcall, int reset_pid);
-void simcall_HANDLER_process_suspend(smx_simcall_t simcall, smx_process_t process);
-void simcall_HANDLER_process_resume(smx_simcall_t simcall, smx_process_t process);
-void simcall_HANDLER_process_set_host(smx_simcall_t simcall, smx_process_t process, sg_host_t dest);
-void simcall_HANDLER_process_join(smx_simcall_t simcall, smx_process_t process, double timeout);
-void simcall_HANDLER_process_sleep(smx_simcall_t simcall, double duration);
-smx_synchro_t simcall_HANDLER_process_execute(smx_simcall_t simcall, const char* name, double flops_amount, double priority, double bound, unsigned long affinity_mask);
-void simcall_HANDLER_process_execution_wait(smx_simcall_t simcall, smx_synchro_t execution);
-smx_process_t simcall_HANDLER_process_restart(smx_simcall_t simcall, smx_process_t process);
-smx_synchro_t simcall_HANDLER_comm_iprobe(smx_simcall_t simcall, smx_rdv_t rdv, int type, int src, int tag, simix_match_func_t match_fun, void* data);
-void simcall_HANDLER_comm_send(smx_simcall_t simcall, smx_process_t sender, smx_rdv_t rdv, double task_size, double rate, void* src_buff, size_t src_buff_size, simix_match_func_t match_fun, simix_copy_data_func_t copy_data_fun, void* data, double timeout);
-smx_synchro_t simcall_HANDLER_comm_isend(smx_simcall_t simcall, smx_process_t sender, smx_rdv_t rdv, double task_size, double rate, void* src_buff, size_t src_buff_size, simix_match_func_t match_fun, simix_clean_func_t clean_fun, simix_copy_data_func_t copy_data_fun, void* data, int detached);
-void simcall_HANDLER_comm_recv(smx_simcall_t simcall, smx_process_t receiver, smx_rdv_t rdv, void* dst_buff, size_t* dst_buff_size, simix_match_func_t match_fun, simix_copy_data_func_t copy_data_fun, void* data, double timeout, double rate);
-smx_synchro_t simcall_HANDLER_comm_irecv(smx_simcall_t simcall, smx_process_t receiver, smx_rdv_t rdv, void* dst_buff, size_t* dst_buff_size, simix_match_func_t match_fun, simix_copy_data_func_t copy_data_fun, void* data, double rate);
-void simcall_HANDLER_comm_waitany(smx_simcall_t simcall, xbt_dynar_t comms);
-void simcall_HANDLER_comm_wait(smx_simcall_t simcall, smx_synchro_t comm, double timeout);
-void simcall_HANDLER_comm_test(smx_simcall_t simcall, smx_synchro_t comm);
-void simcall_HANDLER_comm_testany(smx_simcall_t simcall, xbt_dynar_t comms);
-smx_mutex_t simcall_HANDLER_mutex_init(smx_simcall_t simcall);
-void simcall_HANDLER_mutex_lock(smx_simcall_t simcall, smx_mutex_t mutex);
-int simcall_HANDLER_mutex_trylock(smx_simcall_t simcall, smx_mutex_t mutex);
-void simcall_HANDLER_mutex_unlock(smx_simcall_t simcall, smx_mutex_t mutex);
-void simcall_HANDLER_cond_wait(smx_simcall_t simcall, smx_cond_t cond, smx_mutex_t mutex);
-void simcall_HANDLER_cond_wait_timeout(smx_simcall_t simcall, smx_cond_t cond, smx_mutex_t mutex, double timeout);
-void simcall_HANDLER_sem_release(smx_simcall_t simcall, smx_sem_t sem);
-int simcall_HANDLER_sem_would_block(smx_simcall_t simcall, smx_sem_t sem);
-void simcall_HANDLER_sem_acquire(smx_simcall_t simcall, smx_sem_t sem);
-void simcall_HANDLER_sem_acquire_timeout(smx_simcall_t simcall, smx_sem_t sem, double timeout);
-int simcall_HANDLER_sem_get_capacity(smx_simcall_t simcall, smx_sem_t sem);
-void simcall_HANDLER_file_read(smx_simcall_t simcall, smx_file_t fd, sg_size_t size, sg_host_t host);
-void simcall_HANDLER_file_write(smx_simcall_t simcall, smx_file_t fd, sg_size_t size, sg_host_t host);
-void simcall_HANDLER_file_open(smx_simcall_t simcall, const char* fullpath, sg_host_t host);
-void simcall_HANDLER_file_close(smx_simcall_t simcall, smx_file_t fd, sg_host_t host);
-sg_size_t simcall_HANDLER_file_get_size(smx_simcall_t simcall, smx_file_t fd);
-sg_size_t simcall_HANDLER_file_tell(smx_simcall_t simcall, smx_file_t fd);
-int simcall_HANDLER_file_seek(smx_simcall_t simcall, smx_file_t fd, sg_offset_t offset, int origin);
-xbt_dynar_t simcall_HANDLER_file_get_info(smx_simcall_t simcall, smx_file_t fd);
-int simcall_HANDLER_file_move(smx_simcall_t simcall, smx_file_t fd, const char* fullpath);
-sg_size_t simcall_HANDLER_storage_get_free_size(smx_simcall_t simcall, smx_storage_t storage);
-sg_size_t simcall_HANDLER_storage_get_used_size(smx_simcall_t simcall, smx_storage_t name);
-xbt_dict_t simcall_HANDLER_asr_get_properties(smx_simcall_t simcall, const char* name);
-int simcall_HANDLER_mc_random(smx_simcall_t simcall, int min, int max);
+XBT_PRIVATE void simcall_HANDLER_host_off(smx_simcall_t simcall, sg_host_t host);
+XBT_PRIVATE void simcall_HANDLER_vm_suspend(smx_simcall_t simcall, sg_host_t ind_vm);
+XBT_PRIVATE void simcall_HANDLER_vm_resume(smx_simcall_t simcall, sg_host_t ind_vm);
+XBT_PRIVATE void simcall_HANDLER_vm_shutdown(smx_simcall_t simcall, sg_host_t ind_vm);
+XBT_PRIVATE void simcall_HANDLER_vm_save(smx_simcall_t simcall, sg_host_t ind_vm);
+XBT_PRIVATE void simcall_HANDLER_vm_restore(smx_simcall_t simcall, sg_host_t ind_vm);
+XBT_PRIVATE void* simcall_HANDLER_process_create(smx_simcall_t simcall, const char* name, xbt_main_func_t code, void* data, const char* hostname, double kill_time, int argc, char** argv, xbt_dict_t properties, int auto_restart);
+XBT_PRIVATE void simcall_HANDLER_process_kill(smx_simcall_t simcall, smx_process_t process);
+XBT_PRIVATE void simcall_HANDLER_process_killall(smx_simcall_t simcall, int reset_pid);
+XBT_PRIVATE void simcall_HANDLER_process_suspend(smx_simcall_t simcall, smx_process_t process);
+XBT_PRIVATE void simcall_HANDLER_process_resume(smx_simcall_t simcall, smx_process_t process);
+XBT_PRIVATE void simcall_HANDLER_process_set_host(smx_simcall_t simcall, smx_process_t process, sg_host_t dest);
+XBT_PRIVATE void simcall_HANDLER_process_join(smx_simcall_t simcall, smx_process_t process, double timeout);
+XBT_PRIVATE void simcall_HANDLER_process_sleep(smx_simcall_t simcall, double duration);
+XBT_PRIVATE smx_synchro_t simcall_HANDLER_process_execute(smx_simcall_t simcall, const char* name, double flops_amount, double priority, double bound, unsigned long affinity_mask);
+XBT_PRIVATE void simcall_HANDLER_process_execution_wait(smx_simcall_t simcall, smx_synchro_t execution);
+XBT_PRIVATE smx_process_t simcall_HANDLER_process_restart(smx_simcall_t simcall, smx_process_t process);
+XBT_PRIVATE smx_synchro_t simcall_HANDLER_comm_iprobe(smx_simcall_t simcall, smx_rdv_t rdv, int type, int src, int tag, simix_match_func_t match_fun, void* data);
+XBT_PRIVATE void simcall_HANDLER_comm_send(smx_simcall_t simcall, smx_process_t sender, smx_rdv_t rdv, double task_size, double rate, void* src_buff, size_t src_buff_size, simix_match_func_t match_fun, simix_copy_data_func_t copy_data_fun, void* data, double timeout);
+XBT_PRIVATE smx_synchro_t simcall_HANDLER_comm_isend(smx_simcall_t simcall, smx_process_t sender, smx_rdv_t rdv, double task_size, double rate, void* src_buff, size_t src_buff_size, simix_match_func_t match_fun, simix_clean_func_t clean_fun, simix_copy_data_func_t copy_data_fun, void* data, int detached);
+XBT_PRIVATE void simcall_HANDLER_comm_recv(smx_simcall_t simcall, smx_process_t receiver, smx_rdv_t rdv, void* dst_buff, size_t* dst_buff_size, simix_match_func_t match_fun, simix_copy_data_func_t copy_data_fun, void* data, double timeout, double rate);
+XBT_PRIVATE smx_synchro_t simcall_HANDLER_comm_irecv(smx_simcall_t simcall, smx_process_t receiver, smx_rdv_t rdv, void* dst_buff, size_t* dst_buff_size, simix_match_func_t match_fun, simix_copy_data_func_t copy_data_fun, void* data, double rate);
+XBT_PRIVATE void simcall_HANDLER_comm_waitany(smx_simcall_t simcall, xbt_dynar_t comms);
+XBT_PRIVATE void simcall_HANDLER_comm_wait(smx_simcall_t simcall, smx_synchro_t comm, double timeout);
+XBT_PRIVATE void simcall_HANDLER_comm_test(smx_simcall_t simcall, smx_synchro_t comm);
+XBT_PRIVATE void simcall_HANDLER_comm_testany(smx_simcall_t simcall, xbt_dynar_t comms);
+XBT_PRIVATE smx_mutex_t simcall_HANDLER_mutex_init(smx_simcall_t simcall);
+XBT_PRIVATE void simcall_HANDLER_mutex_lock(smx_simcall_t simcall, smx_mutex_t mutex);
+XBT_PRIVATE int simcall_HANDLER_mutex_trylock(smx_simcall_t simcall, smx_mutex_t mutex);
+XBT_PRIVATE void simcall_HANDLER_mutex_unlock(smx_simcall_t simcall, smx_mutex_t mutex);
+XBT_PRIVATE void simcall_HANDLER_cond_wait(smx_simcall_t simcall, smx_cond_t cond, smx_mutex_t mutex);
+XBT_PRIVATE void simcall_HANDLER_cond_wait_timeout(smx_simcall_t simcall, smx_cond_t cond, smx_mutex_t mutex, double timeout);
+XBT_PRIVATE void simcall_HANDLER_sem_release(smx_simcall_t simcall, smx_sem_t sem);
+XBT_PRIVATE int simcall_HANDLER_sem_would_block(smx_simcall_t simcall, smx_sem_t sem);
+XBT_PRIVATE void simcall_HANDLER_sem_acquire(smx_simcall_t simcall, smx_sem_t sem);
+XBT_PRIVATE void simcall_HANDLER_sem_acquire_timeout(smx_simcall_t simcall, smx_sem_t sem, double timeout);
+XBT_PRIVATE int simcall_HANDLER_sem_get_capacity(smx_simcall_t simcall, smx_sem_t sem);
+XBT_PRIVATE void simcall_HANDLER_file_read(smx_simcall_t simcall, smx_file_t fd, sg_size_t size, sg_host_t host);
+XBT_PRIVATE void simcall_HANDLER_file_write(smx_simcall_t simcall, smx_file_t fd, sg_size_t size, sg_host_t host);
+XBT_PRIVATE void simcall_HANDLER_file_open(smx_simcall_t simcall, const char* fullpath, sg_host_t host);
+XBT_PRIVATE void simcall_HANDLER_file_close(smx_simcall_t simcall, smx_file_t fd, sg_host_t host);
+XBT_PRIVATE sg_size_t simcall_HANDLER_file_get_size(smx_simcall_t simcall, smx_file_t fd);
+XBT_PRIVATE sg_size_t simcall_HANDLER_file_tell(smx_simcall_t simcall, smx_file_t fd);
+XBT_PRIVATE int simcall_HANDLER_file_seek(smx_simcall_t simcall, smx_file_t fd, sg_offset_t offset, int origin);
+XBT_PRIVATE xbt_dynar_t simcall_HANDLER_file_get_info(smx_simcall_t simcall, smx_file_t fd);
+XBT_PRIVATE int simcall_HANDLER_file_move(smx_simcall_t simcall, smx_file_t fd, const char* fullpath);
+XBT_PRIVATE sg_size_t simcall_HANDLER_storage_get_free_size(smx_simcall_t simcall, smx_storage_t storage);
+XBT_PRIVATE sg_size_t simcall_HANDLER_storage_get_used_size(smx_simcall_t simcall, smx_storage_t name);
+XBT_PRIVATE xbt_dict_t simcall_HANDLER_asr_get_properties(smx_simcall_t simcall, const char* name);
+XBT_PRIVATE int simcall_HANDLER_mc_random(smx_simcall_t simcall, int min, int max);
 #ifdef HAVE_LATENCY_BOUND_TRACKING
 
 #endif
 
 #ifdef HAVE_MC
-mc_snapshot_t simcall_HANDLER_mc_snapshot(smx_simcall_t simcall);
-int simcall_HANDLER_mc_compare_snapshots(smx_simcall_t simcall, mc_snapshot_t s1, mc_snapshot_t s2);
+XBT_PRIVATE mc_snapshot_t simcall_HANDLER_mc_snapshot(smx_simcall_t simcall);
+XBT_PRIVATE int simcall_HANDLER_mc_compare_snapshots(smx_simcall_t simcall, mc_snapshot_t s1, mc_snapshot_t s2);
 #endif
index 76752d7..a290148 100644 (file)
@@ -13,6 +13,7 @@
  * That's not about http://en.wikipedia.org/wiki/Poop, despite the odor :)
  */
 
+#include <xbt/base.h>
 #include "smx_private.h"
 #ifdef HAVE_MC
 #include "mc/mc_forward.h"
index cedca92..26e3662 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _POPPING_PRIVATE_H
 #define _POPPING_PRIVATE_H
 
+#include <xbt/base.h>
+
 SG_BEGIN_DECL()
 
 /********************************* Simcalls *********************************/
@@ -59,10 +61,10 @@ typedef struct s_smx_simcall {
 
 /******************************** General *************************************/
 
-void SIMIX_simcall_answer(smx_simcall_t);
-void SIMIX_simcall_handle(smx_simcall_t, int);
-void SIMIX_simcall_exit(smx_synchro_t);
-const char *SIMIX_simcall_name(e_smx_simcall_t kind);
+XBT_PRIVATE void SIMIX_simcall_answer(smx_simcall_t);
+XBT_PRIVATE void SIMIX_simcall_handle(smx_simcall_t, int);
+XBT_PRIVATE void SIMIX_simcall_exit(smx_synchro_t);
+XBT_PRIVATE const char *SIMIX_simcall_name(e_smx_simcall_t kind);
 
 SG_END_DECL()
 
index f7f776d..aa2a54d 100755 (executable)
@@ -177,7 +177,7 @@ class Simcall(object):
       
   def handler_prototype(self):
       if self.need_handler:
-          return "%s simcall_HANDLER_%s(smx_simcall_t simcall%s);"%(self.res.rettype() if self.call_kind == 'Func' else 'void', 
+          return "XBT_PRIVATE %s simcall_HANDLER_%s(smx_simcall_t simcall%s);"%(self.res.rettype() if self.call_kind == 'Func' else 'void', 
                                                                     self.name, 
                                                                     ''.join(', %s %s'%(arg.rettype(), arg.name) 
                     for i, arg in enumerate(self.args)))
@@ -279,6 +279,7 @@ if __name__=='__main__':
   
   fd = header("popping_generated.c")
   
+  fd.write('#include <xbt/base.h>\n');
   fd.write('#include "smx_private.h"\n');
   fd.write('#ifdef HAVE_MC\n');
   fd.write('#include "mc/mc_forward.h"\n');
index 9adeeac..e447ed3 100644 (file)
@@ -18,6 +18,7 @@
 
 #ifdef _WIN32
 #include <windows.h>
+#include <malloc.h>
 #else
 #include <sys/mman.h>
 #endif
 #define _aligned_free  __mingw_aligned_free 
 #endif //MINGW
 
-#if defined(_XBT_WIN32)
-#include <malloc.h>
-#endif
-
 #ifdef HAVE_VALGRIND_VALGRIND_H
 # include <valgrind/valgrind.h>
 #endif
@@ -45,7 +42,7 @@ int smx_context_stack_size_was_set = 0;
 int smx_context_guard_size;
 int smx_context_guard_size_was_set = 0;
 #ifdef HAVE_THREAD_LOCAL_STORAGE
-static __thread smx_context_t smx_current_context_parallel;
+static XBT_THREAD_LOCAL smx_context_t smx_current_context_parallel;
 #else
 static xbt_os_thread_key_t smx_current_context_key = 0;
 #endif
index 0161c31..60fad15 100644 (file)
@@ -552,7 +552,7 @@ static void smx_ctx_raw_suspend_parallel(smx_context_t context)
     XBT_DEBUG("No more processes to run");
 
     unsigned long worker_id =
-        (unsigned long) xbt_os_thread_get_specific(raw_worker_id_key);
+        (unsigned long)(uintptr_t) xbt_os_thread_get_specific(raw_worker_id_key);
 
     next_context = (smx_context_t)raw_workers_context[worker_id];
     XBT_DEBUG("Restoring worker stack %lu (working threads = %lu)",
@@ -574,7 +574,7 @@ static void smx_ctx_raw_resume_parallel(smx_process_t first_process)
 {
 #ifdef CONTEXT_THREADS
   unsigned long worker_id = __sync_fetch_and_add(&raw_threads_working, 1);
-  xbt_os_thread_set_specific(raw_worker_id_key, (void*) worker_id);
+  xbt_os_thread_set_specific(raw_worker_id_key, (void*)(uintptr_t) worker_id);
   smx_ctx_raw_t worker_context = (smx_ctx_raw_t)SIMIX_context_self();
   raw_workers_context[worker_id] = worker_context;
   XBT_DEBUG("Saving worker stack %lu", worker_id);
index bb3b90b..da7cb74 100644 (file)
@@ -114,7 +114,7 @@ void SIMIX_init_application(void){
  */
 void SIMIX_launch_application(const char *file)
 {
-  _XBT_GNUC_UNUSED int parse_status;
+  XBT_ATTRIB_UNUSED int parse_status;
   xbt_assert(simix_global,
               "SIMIX_global_init has to be called before SIMIX_launch_application.");
 
index d78fe0e..d3337a3 100644 (file)
 #include "mc/mc_protocol.h"
 #include "mc/mc_client.h"
 #endif
+
+#ifdef HAVE_MC
+#include <stdlib.h>
+#include "mc/mc_protocol.h"
+#endif 
+
 #include "mc/mc_record.h"
 
 #ifdef HAVE_SMPI
@@ -151,6 +157,10 @@ XBT_INLINE double SIMIX_timer_next(void)
  */
 void SIMIX_global_init(int *argc, char **argv)
 {
+#ifdef HAVE_MC
+  _sg_do_model_check = getenv(MC_ENV_VARIABLE) != NULL;
+#endif
+
   s_smx_process_t proc;
 
   if (!simix_global) {
@@ -228,6 +238,7 @@ void SIMIX_global_init(int *argc, char **argv)
     exit(0);
 }
 
+int smx_cleaned = 0;
 /**
  * \ingroup SIMIX_API
  * \brief Clean the SIMIX simulation
@@ -236,12 +247,11 @@ void SIMIX_global_init(int *argc, char **argv)
  */
 void SIMIX_clean(void)
 {
-  static int cleaned = 0;
 #ifdef TIME_BENCH_PER_SR
   smx_ctx_raw_new_sr();
 #endif
-  if (cleaned) return; // to avoid double cleaning by java and C
-  cleaned = 1;
+  if (smx_cleaned) return; // to avoid double cleaning by java and C
+  smx_cleaned = 1;
   XBT_DEBUG("SIMIX_clean called. Simulation's over.");
   if (!xbt_dynar_is_empty(simix_global->process_to_run) && SIMIX_get_clock() == 0.0) {
          XBT_CRITICAL("   ");
index 471f3ed..b0154cb 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _SIMIX_HOST_PRIVATE_H
 #define _SIMIX_HOST_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "simgrid/simix.h"
 #include "popping_private.h"
 
@@ -19,11 +21,11 @@ typedef struct s_smx_host_priv {
   xbt_dynar_t boot_processes;
 } s_smx_host_priv_t;
 
-void _SIMIX_host_free_process_arg(void *);
-void SIMIX_host_create(const char *name);
-void SIMIX_host_destroy(void *host);
+XBT_PRIVATE void _SIMIX_host_free_process_arg(void *);
+XBT_PRIVATE void SIMIX_host_create(const char *name);
+XBT_PRIVATE void SIMIX_host_destroy(void *host);
 
-void SIMIX_host_add_auto_restart_process(sg_host_t host,
+XBT_PRIVATE void SIMIX_host_add_auto_restart_process(sg_host_t host,
                                          const char *name,
                                          xbt_main_func_t code,
                                          void *data,
@@ -33,76 +35,76 @@ void SIMIX_host_add_auto_restart_process(sg_host_t host,
                                          xbt_dict_t properties,
                                          int auto_restart);
 
-void SIMIX_host_restart_processes(sg_host_t host);
-void SIMIX_host_autorestart(sg_host_t host);
-xbt_dict_t SIMIX_host_get_properties(sg_host_t host);
-int SIMIX_host_get_core(sg_host_t host);
-xbt_swag_t SIMIX_host_get_process_list(sg_host_t host);
-double SIMIX_host_get_speed(sg_host_t host);
-double SIMIX_host_get_available_speed(sg_host_t host);
-int SIMIX_host_get_state(sg_host_t host);
-double SIMIX_host_get_current_power_peak(sg_host_t host);
-double SIMIX_host_get_power_peak_at(sg_host_t host, int pstate_index);
-int SIMIX_host_get_nb_pstates(sg_host_t host);
-double SIMIX_host_get_consumed_energy(sg_host_t host);
-double SIMIX_host_get_wattmin_at(sg_host_t host,int pstate);
-double SIMIX_host_get_wattmax_at(sg_host_t host,int pstate);
-void SIMIX_host_set_pstate(sg_host_t host, int pstate_index);
-int SIMIX_host_get_pstate(sg_host_t host);
-smx_synchro_t SIMIX_process_execute(smx_process_t issuer, const char *name,
+XBT_PRIVATE void SIMIX_host_restart_processes(sg_host_t host);
+XBT_PRIVATE void SIMIX_host_autorestart(sg_host_t host);
+XBT_PRIVATE xbt_dict_t SIMIX_host_get_properties(sg_host_t host);
+XBT_PRIVATE int SIMIX_host_get_core(sg_host_t host);
+XBT_PRIVATE xbt_swag_t SIMIX_host_get_process_list(sg_host_t host);
+XBT_PRIVATE double SIMIX_host_get_speed(sg_host_t host);
+XBT_PRIVATE double SIMIX_host_get_available_speed(sg_host_t host);
+XBT_PRIVATE int SIMIX_host_get_state(sg_host_t host);
+XBT_PRIVATE double SIMIX_host_get_current_power_peak(sg_host_t host);
+XBT_PRIVATE double SIMIX_host_get_power_peak_at(sg_host_t host, int pstate_index);
+XBT_PRIVATE int SIMIX_host_get_nb_pstates(sg_host_t host);
+XBT_PRIVATE double SIMIX_host_get_consumed_energy(sg_host_t host);
+XBT_PRIVATE double SIMIX_host_get_wattmin_at(sg_host_t host,int pstate);
+XBT_PRIVATE double SIMIX_host_get_wattmax_at(sg_host_t host,int pstate);
+XBT_PRIVATE void SIMIX_host_set_pstate(sg_host_t host, int pstate_index);
+XBT_PRIVATE int SIMIX_host_get_pstate(sg_host_t host);
+XBT_PRIVATE smx_synchro_t SIMIX_process_execute(smx_process_t issuer, const char *name,
     double flops_amount, double priority, double bound, unsigned long affinity_mask);
-smx_synchro_t SIMIX_process_parallel_execute(const char *name,
+XBT_PRIVATE smx_synchro_t SIMIX_process_parallel_execute(const char *name,
     int host_nb, sg_host_t *host_list,
     double *flops_amount, double *bytes_amount,
     double amount, double rate);
-void SIMIX_process_execution_destroy(smx_synchro_t synchro);
-void SIMIX_process_execution_cancel(smx_synchro_t synchro);
-double SIMIX_process_execution_get_remains(smx_synchro_t synchro);
-e_smx_state_t SIMIX_process_execution_get_state(smx_synchro_t synchro);
-void SIMIX_process_execution_set_priority(smx_synchro_t synchro, double priority);
-void SIMIX_process_execution_set_bound(smx_synchro_t synchro, double bound);
-void SIMIX_process_execution_set_affinity(smx_synchro_t synchro, sg_host_t host, unsigned long mask);
-xbt_dynar_t SIMIX_host_get_attached_storage_list(sg_host_t host);
+XBT_PRIVATE void SIMIX_process_execution_destroy(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_process_execution_cancel(smx_synchro_t synchro);
+XBT_PRIVATE double SIMIX_process_execution_get_remains(smx_synchro_t synchro);
+XBT_PRIVATE e_smx_state_t SIMIX_process_execution_get_state(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_process_execution_set_priority(smx_synchro_t synchro, double priority);
+XBT_PRIVATE void SIMIX_process_execution_set_bound(smx_synchro_t synchro, double bound);
+XBT_PRIVATE void SIMIX_process_execution_set_affinity(smx_synchro_t synchro, sg_host_t host, unsigned long mask);
+XBT_PRIVATE xbt_dynar_t SIMIX_host_get_attached_storage_list(sg_host_t host);
 
-void SIMIX_host_execution_suspend(smx_synchro_t synchro);
-void SIMIX_host_execution_resume(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_host_execution_suspend(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_host_execution_resume(smx_synchro_t synchro);
 
-void SIMIX_post_host_execute(smx_synchro_t synchro);
-void SIMIX_set_category(smx_synchro_t synchro, const char *category);
+XBT_PRIVATE void SIMIX_post_host_execute(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_set_category(smx_synchro_t synchro, const char *category);
 
 /* vm related stuff */
-sg_host_t SIMIX_vm_create(const char *name, sg_host_t ind_phys_host);
+XBT_PRIVATE sg_host_t SIMIX_vm_create(const char *name, sg_host_t ind_phys_host);
 
-void SIMIX_vm_destroy(sg_host_t ind_vm);
+XBT_PRIVATE void SIMIX_vm_destroy(sg_host_t ind_vm);
 // --
-void SIMIX_vm_resume(sg_host_t ind_vm, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_vm_resume(sg_host_t ind_vm, smx_process_t issuer);
 
-void SIMIX_vm_suspend(sg_host_t ind_vm, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_vm_suspend(sg_host_t ind_vm, smx_process_t issuer);
 // --
-void SIMIX_vm_save(sg_host_t ind_vm, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_vm_save(sg_host_t ind_vm, smx_process_t issuer);
 
-void SIMIX_vm_restore(sg_host_t ind_vm, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_vm_restore(sg_host_t ind_vm, smx_process_t issuer);
 // --
-void SIMIX_vm_start(sg_host_t ind_vm);
+XBT_PRIVATE void SIMIX_vm_start(sg_host_t ind_vm);
 
-void SIMIX_vm_shutdown(sg_host_t ind_vm, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_vm_shutdown(sg_host_t ind_vm, smx_process_t issuer);
 // --
 
-int SIMIX_vm_get_state(sg_host_t ind_vm);
+XBT_PRIVATE int SIMIX_vm_get_state(sg_host_t ind_vm);
 // --
-void SIMIX_vm_migrate(sg_host_t ind_vm, sg_host_t ind_dst_pm);
+XBT_PRIVATE void SIMIX_vm_migrate(sg_host_t ind_vm, sg_host_t ind_dst_pm);
 
-void *SIMIX_vm_get_pm(sg_host_t ind_vm);
+XBT_PRIVATE void *SIMIX_vm_get_pm(sg_host_t ind_vm);
 
-void SIMIX_vm_set_bound(sg_host_t ind_vm, double bound);
+XBT_PRIVATE void SIMIX_vm_set_bound(sg_host_t ind_vm, double bound);
 
-void SIMIX_vm_set_affinity(sg_host_t ind_vm, sg_host_t ind_pm, unsigned long mask);
+XBT_PRIVATE void SIMIX_vm_set_affinity(sg_host_t ind_vm, sg_host_t ind_pm, unsigned long mask);
 
-void SIMIX_vm_migratefrom_resumeto(sg_host_t vm, sg_host_t src_pm, sg_host_t dst_pm);
+XBT_PRIVATE void SIMIX_vm_migratefrom_resumeto(sg_host_t vm, sg_host_t src_pm, sg_host_t dst_pm);
 
-void SIMIX_host_get_params(sg_host_t ind_vm, vm_params_t params);
+XBT_PRIVATE void SIMIX_host_get_params(sg_host_t ind_vm, vm_params_t params);
 
-void SIMIX_host_set_params(sg_host_t ind_vm, vm_params_t params);
+XBT_PRIVATE void SIMIX_host_set_params(sg_host_t ind_vm, vm_params_t params);
 
 SG_END_DECL()
 
index e0e6b79..7071717 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _SIMIX_IO_PRIVATE_H
 #define _SIMIX_IO_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "simgrid/simix.h"
 #include "popping_private.h"
 
@@ -20,26 +22,26 @@ static inline smx_storage_priv_t SIMIX_storage_priv(smx_storage_t storage){
   return (smx_storage_priv_t) xbt_lib_get_level(storage, SIMIX_STORAGE_LEVEL);
 }
 
-smx_storage_t SIMIX_storage_create(const char *name, void *storage, void *data);
-void SIMIX_storage_destroy(void *s);
-smx_synchro_t SIMIX_file_read(smx_file_t fd, sg_size_t size, sg_host_t host);
-smx_synchro_t SIMIX_file_write(smx_file_t fd, sg_size_t size, sg_host_t host);
-smx_synchro_t SIMIX_file_open(const char* fullpath, sg_host_t host);
-smx_synchro_t SIMIX_file_close(smx_file_t fd, sg_host_t host);
-int SIMIX_file_unlink(smx_file_t fd, sg_host_t host);
-sg_size_t SIMIX_file_get_size(smx_process_t process, smx_file_t fd);
-sg_size_t SIMIX_file_tell(smx_process_t process, smx_file_t fd);
-xbt_dynar_t SIMIX_file_get_info(smx_process_t process, smx_file_t fd);
-int SIMIX_file_seek(smx_process_t process, smx_file_t fd, sg_offset_t offset, int origin);
-int SIMIX_file_move(smx_process_t process, smx_file_t fd, const char* fullpath);
-
-sg_size_t SIMIX_storage_get_free_size(smx_process_t process, smx_storage_t storage);
-sg_size_t SIMIX_storage_get_used_size(smx_process_t process, smx_storage_t storage);
-
-xbt_dict_t SIMIX_storage_get_properties(smx_storage_t storage);
-
-void SIMIX_post_io(smx_synchro_t synchro);
-void SIMIX_io_destroy(smx_synchro_t synchro);
-void SIMIX_io_finish(smx_synchro_t synchro);
+XBT_PRIVATE smx_storage_t SIMIX_storage_create(const char *name, void *storage, void *data);
+XBT_PRIVATE void SIMIX_storage_destroy(void *s);
+XBT_PRIVATE smx_synchro_t SIMIX_file_read(smx_file_t fd, sg_size_t size, sg_host_t host);
+XBT_PRIVATE smx_synchro_t SIMIX_file_write(smx_file_t fd, sg_size_t size, sg_host_t host);
+XBT_PRIVATE smx_synchro_t SIMIX_file_open(const char* fullpath, sg_host_t host);
+XBT_PRIVATE smx_synchro_t SIMIX_file_close(smx_file_t fd, sg_host_t host);
+XBT_PRIVATE int SIMIX_file_unlink(smx_file_t fd, sg_host_t host);
+XBT_PRIVATE sg_size_t SIMIX_file_get_size(smx_process_t process, smx_file_t fd);
+XBT_PRIVATE sg_size_t SIMIX_file_tell(smx_process_t process, smx_file_t fd);
+XBT_PRIVATE xbt_dynar_t SIMIX_file_get_info(smx_process_t process, smx_file_t fd);
+XBT_PRIVATE int SIMIX_file_seek(smx_process_t process, smx_file_t fd, sg_offset_t offset, int origin);
+XBT_PRIVATE int SIMIX_file_move(smx_process_t process, smx_file_t fd, const char* fullpath);
+
+XBT_PRIVATE sg_size_t SIMIX_storage_get_free_size(smx_process_t process, smx_storage_t storage);
+XBT_PRIVATE sg_size_t SIMIX_storage_get_used_size(smx_process_t process, smx_storage_t storage);
+
+XBT_PRIVATE xbt_dict_t SIMIX_storage_get_properties(smx_storage_t storage);
+
+XBT_PRIVATE void SIMIX_post_io(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_io_destroy(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_io_finish(smx_synchro_t synchro);
 
 #endif
index da8704f..129cfd7 100644 (file)
@@ -9,7 +9,6 @@
 #include "mc/mc.h"
 #include "mc/mc_replay.h"
 #include "xbt/dict.h"
-#include "smpi/private.h"
 
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(simix_network, simix,
                                 "SIMIX network-related synchronization");
index 93778b1..0177f06 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _SIMIX_NETWORK_PRIVATE_H
 #define _SIMIX_NETWORK_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "simgrid/simix.h"
 #include "popping_private.h"
 
@@ -19,38 +21,38 @@ typedef struct s_smx_rvpoint {
   xbt_fifo_t done_comm_fifo;//messages already received in the permanent receive mode
 } s_smx_rvpoint_t;
 
-void SIMIX_network_init(void);
-void SIMIX_network_exit(void);
+XBT_PRIVATE void SIMIX_network_init(void);
+XBT_PRIVATE void SIMIX_network_exit(void);
 
 #ifdef HAVE_LATENCY_BOUND_TRACKING
 XBT_PUBLIC(int) SIMIX_comm_is_latency_bounded(smx_synchro_t comm);
 #endif
 
-smx_rdv_t SIMIX_rdv_create(const char *name);
-void SIMIX_rdv_destroy(smx_rdv_t rdv);
-smx_rdv_t SIMIX_rdv_get_by_name(const char *name);
-void SIMIX_rdv_remove(smx_rdv_t rdv, smx_synchro_t comm);
-int SIMIX_rdv_comm_count_by_host(smx_rdv_t rdv, sg_host_t host);
-smx_synchro_t SIMIX_rdv_get_head(smx_rdv_t rdv);
-void SIMIX_rdv_set_receiver(smx_rdv_t rdv, smx_process_t proc);
-smx_process_t SIMIX_rdv_get_receiver(smx_rdv_t rdv);
-smx_synchro_t SIMIX_comm_irecv(smx_process_t dst_proc, smx_rdv_t rdv,
+XBT_PRIVATE smx_rdv_t SIMIX_rdv_create(const char *name);
+XBT_PRIVATE void SIMIX_rdv_destroy(smx_rdv_t rdv);
+XBT_PRIVATE smx_rdv_t SIMIX_rdv_get_by_name(const char *name);
+XBT_PRIVATE void SIMIX_rdv_remove(smx_rdv_t rdv, smx_synchro_t comm);
+XBT_PRIVATE int SIMIX_rdv_comm_count_by_host(smx_rdv_t rdv, sg_host_t host);
+XBT_PRIVATE smx_synchro_t SIMIX_rdv_get_head(smx_rdv_t rdv);
+XBT_PRIVATE void SIMIX_rdv_set_receiver(smx_rdv_t rdv, smx_process_t proc);
+XBT_PRIVATE smx_process_t SIMIX_rdv_get_receiver(smx_rdv_t rdv);
+XBT_PRIVATE smx_synchro_t SIMIX_comm_irecv(smx_process_t dst_proc, smx_rdv_t rdv,
                               void *dst_buff, size_t *dst_buff_size,
                               int (*)(void *, void *, smx_synchro_t),
                               void (*copy_data_fun)(smx_synchro_t, void*, size_t),
                               void *data, double rate);
-void SIMIX_comm_destroy(smx_synchro_t synchro);
-void SIMIX_comm_destroy_internal_actions(smx_synchro_t synchro);
-smx_synchro_t SIMIX_comm_iprobe(smx_process_t dst_proc, smx_rdv_t rdv, int type, int src,
+XBT_PRIVATE void SIMIX_comm_destroy(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_comm_destroy_internal_actions(smx_synchro_t synchro);
+XBT_PRIVATE smx_synchro_t SIMIX_comm_iprobe(smx_process_t dst_proc, smx_rdv_t rdv, int type, int src,
                               int tag, int (*match_fun)(void *, void *, smx_synchro_t), void *data);
-void SIMIX_post_comm(smx_synchro_t synchro);
-void SIMIX_comm_cancel(smx_synchro_t synchro);
-double SIMIX_comm_get_remains(smx_synchro_t synchro);
-e_smx_state_t SIMIX_comm_get_state(smx_synchro_t synchro);
-void SIMIX_comm_suspend(smx_synchro_t synchro);
-void SIMIX_comm_resume(smx_synchro_t synchro);
-smx_process_t SIMIX_comm_get_src_proc(smx_synchro_t synchro);
-smx_process_t SIMIX_comm_get_dst_proc(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_post_comm(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_comm_cancel(smx_synchro_t synchro);
+XBT_PRIVATE double SIMIX_comm_get_remains(smx_synchro_t synchro);
+XBT_PRIVATE e_smx_state_t SIMIX_comm_get_state(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_comm_suspend(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_comm_resume(smx_synchro_t synchro);
+XBT_PRIVATE smx_process_t SIMIX_comm_get_src_proc(smx_synchro_t synchro);
+XBT_PRIVATE smx_process_t SIMIX_comm_get_dst_proc(smx_synchro_t synchro);
 
 #endif
 
index dbd51ad..d908a7d 100644 (file)
@@ -9,6 +9,7 @@
 
 #include "simgrid/simix.h"
 #include "surf/surf.h"
+#include "xbt/base.h"
 #include "xbt/fifo.h"
 #include "xbt/swag.h"
 #include "xbt/dict.h"
@@ -34,7 +35,7 @@ SG_BEGIN_DECL()
 //#define TIME_BENCH_ENTIRE_SRS /* more general benchmark than TIME_BENCH_PER_SR. It aims to measure the total time spent in a whole scheduling round (including synchro costs)*/
 
 #ifdef TIME_BENCH_PER_SR
-void smx_ctx_raw_new_sr(void);
+XBT_PRIVATE void smx_ctx_raw_new_sr(void);
 #endif
 /********************************** Simix Global ******************************/
 typedef struct s_smx_global {
@@ -61,7 +62,7 @@ typedef struct s_smx_global {
 } s_smx_global_t, *smx_global_t;
 
 XBT_PUBLIC_DATA(smx_global_t) simix_global;
-extern unsigned long simix_process_maxpid;
+extern XBT_PRIVATE unsigned long simix_process_maxpid;
 
 XBT_PUBLIC(void) SIMIX_clean(void);
 
@@ -193,8 +194,8 @@ typedef struct s_smx_synchro {
   char *category;                     /* simix action category for instrumentation */
 } s_smx_synchro_t;
 
-void SIMIX_context_mod_init(void);
-void SIMIX_context_mod_exit(void);
+XBT_PRIVATE void SIMIX_context_mod_init(void);
+XBT_PRIVATE void SIMIX_context_mod_exit(void);
 
 #ifndef WIN32
 XBT_PUBLIC_DATA(char sigsegv_stack[SIGSTKSZ]);
@@ -210,18 +211,18 @@ XBT_PUBLIC_DATA(char sigsegv_stack[SIGSTKSZ]);
 # define smx_context_usable_stack_size smx_context_stack_size
 #endif
 
-void *SIMIX_context_stack_new(void);
-void SIMIX_context_stack_delete(void *stack);
+XBT_PRIVATE void *SIMIX_context_stack_new(void);
+XBT_PRIVATE void SIMIX_context_stack_delete(void *stack);
 
-void SIMIX_context_set_current(smx_context_t context);
-smx_context_t SIMIX_context_get_current(void);
+XBT_PRIVATE void SIMIX_context_set_current(smx_context_t context);
+XBT_PRIVATE smx_context_t SIMIX_context_get_current(void);
 
 /* All factories init */
 
-void SIMIX_ctx_thread_factory_init(smx_context_factory_t *factory);
-void SIMIX_ctx_sysv_factory_init(smx_context_factory_t *factory);
-void SIMIX_ctx_raw_factory_init(smx_context_factory_t *factory);
-void SIMIX_ctx_boost_factory_init(smx_context_factory_t *factory);
+XBT_PRIVATE void SIMIX_ctx_thread_factory_init(smx_context_factory_t *factory);
+XBT_PRIVATE void SIMIX_ctx_sysv_factory_init(smx_context_factory_t *factory);
+XBT_PRIVATE void SIMIX_ctx_raw_factory_init(smx_context_factory_t *factory);
+XBT_PRIVATE void SIMIX_ctx_boost_factory_init(smx_context_factory_t *factory);
 
 /* ****************************** */
 /* context manipulation functions */
@@ -327,7 +328,7 @@ static XBT_INLINE smx_process_t SIMIX_context_get_process(smx_context_t context)
 
 XBT_PUBLIC(int) SIMIX_process_get_maxpid(void);
 
-void SIMIX_post_create_environment(void);
+XBT_PRIVATE void SIMIX_post_create_environment(void);
 
 SG_END_DECL()
 
index 6d19ddd..f537925 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _SIMIX_PROCESS_PRIVATE_H
 #define _SIMIX_PROCESS_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "simgrid/simix.h"
 #include "popping_private.h"
 
@@ -62,7 +64,7 @@ typedef struct s_smx_process {
 } s_smx_process_t;
 
 
-smx_process_t SIMIX_process_create(
+XBT_PRIVATE smx_process_t SIMIX_process_create(
                           const char *name,
                           xbt_main_func_t code,
                           void *data,
@@ -72,39 +74,39 @@ smx_process_t SIMIX_process_create(
                           xbt_dict_t properties,
                           int auto_restart,
                           smx_process_t parent_process);
-void SIMIX_process_runall(void);
-void SIMIX_process_kill(smx_process_t process, smx_process_t issuer);
-void SIMIX_process_killall(smx_process_t issuer, int reset_pid);
-smx_process_t SIMIX_process_create_from_wrapper(smx_process_arg_t args);
-void SIMIX_create_maestro_process(void);
-void SIMIX_process_stop(smx_process_t arg);
-void SIMIX_process_cleanup(smx_process_t arg);
-void SIMIX_process_empty_trash(void);
-void SIMIX_process_yield(smx_process_t self);
-xbt_running_ctx_t *SIMIX_process_get_running_context(void);
-void SIMIX_process_exception_terminate(xbt_ex_t * e);
-void SIMIX_process_change_host(smx_process_t process,
+XBT_PRIVATE void SIMIX_process_runall(void);
+XBT_PRIVATE void SIMIX_process_kill(smx_process_t process, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_process_killall(smx_process_t issuer, int reset_pid);
+XBT_PRIVATE smx_process_t SIMIX_process_create_from_wrapper(smx_process_arg_t args);
+XBT_PRIVATE void SIMIX_create_maestro_process(void);
+XBT_PRIVATE void SIMIX_process_stop(smx_process_t arg);
+XBT_PRIVATE void SIMIX_process_cleanup(smx_process_t arg);
+XBT_PRIVATE void SIMIX_process_empty_trash(void);
+XBT_PRIVATE void SIMIX_process_yield(smx_process_t self);
+XBT_PRIVATE xbt_running_ctx_t *SIMIX_process_get_running_context(void);
+XBT_PRIVATE void SIMIX_process_exception_terminate(xbt_ex_t * e);
+XBT_PRIVATE void SIMIX_process_change_host(smx_process_t process,
              sg_host_t dest);
-smx_synchro_t SIMIX_process_suspend(smx_process_t process, smx_process_t issuer);
-void SIMIX_process_resume(smx_process_t process, smx_process_t issuer);
-int SIMIX_process_get_PID(smx_process_t self);
-int SIMIX_process_get_PPID(smx_process_t self);
-void* SIMIX_process_get_data(smx_process_t process);
-void SIMIX_process_set_data(smx_process_t process, void *data);
-sg_host_t SIMIX_process_get_host(smx_process_t process);
-const char* SIMIX_process_get_name(smx_process_t process);
-smx_process_t SIMIX_process_get_by_name(const char* name);
-int SIMIX_process_is_suspended(smx_process_t process);
-xbt_dict_t SIMIX_process_get_properties(smx_process_t process);
-smx_synchro_t SIMIX_process_join(smx_process_t issuer, smx_process_t process, double timeout);
-smx_synchro_t SIMIX_process_sleep(smx_process_t process, double duration);
-void SIMIX_post_process_sleep(smx_synchro_t synchro);
-
-void SIMIX_process_sleep_suspend(smx_synchro_t synchro);
-void SIMIX_process_sleep_resume(smx_synchro_t synchro);
-void SIMIX_process_sleep_destroy(smx_synchro_t synchro);
-void SIMIX_process_auto_restart_set(smx_process_t process, int auto_restart);
-smx_process_t SIMIX_process_restart(smx_process_t process, smx_process_t issuer);
+XBT_PRIVATE smx_synchro_t SIMIX_process_suspend(smx_process_t process, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_process_resume(smx_process_t process, smx_process_t issuer);
+XBT_PRIVATE int SIMIX_process_get_PID(smx_process_t self);
+XBT_PRIVATE int SIMIX_process_get_PPID(smx_process_t self);
+XBT_PRIVATE void* SIMIX_process_get_data(smx_process_t process);
+XBT_PRIVATE void SIMIX_process_set_data(smx_process_t process, void *data);
+XBT_PRIVATE sg_host_t SIMIX_process_get_host(smx_process_t process);
+XBT_PRIVATE const char* SIMIX_process_get_name(smx_process_t process);
+XBT_PRIVATE smx_process_t SIMIX_process_get_by_name(const char* name);
+XBT_PRIVATE int SIMIX_process_is_suspended(smx_process_t process);
+XBT_PRIVATE xbt_dict_t SIMIX_process_get_properties(smx_process_t process);
+XBT_PRIVATE smx_synchro_t SIMIX_process_join(smx_process_t issuer, smx_process_t process, double timeout);
+XBT_PRIVATE smx_synchro_t SIMIX_process_sleep(smx_process_t process, double duration);
+XBT_PRIVATE void SIMIX_post_process_sleep(smx_synchro_t synchro);
+
+XBT_PRIVATE void SIMIX_process_sleep_suspend(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_process_sleep_resume(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_process_sleep_destroy(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_process_auto_restart_set(smx_process_t process, int auto_restart);
+XBT_PRIVATE smx_process_t SIMIX_process_restart(smx_process_t process, smx_process_t issuer);
 
 SG_END_DECL()
 
index 9907e41..d6da804 100644 (file)
@@ -7,6 +7,7 @@
 #ifndef _SIMIX_SYNCHRO_PRIVATE_H
 #define _SIMIX_SYNCHRO_PRIVATE_H
 
+#include "xbt/base.h"
 #include "xbt/swag.h"
 #include "xbt/xbt_os_thread.h"
 
@@ -26,24 +27,24 @@ typedef struct s_smx_sem {
   xbt_swag_t sleeping;          /* list of sleeping process */
 } s_smx_sem_t;
 
-void SIMIX_post_synchro(smx_synchro_t synchro);
-void SIMIX_synchro_stop_waiting(smx_process_t process, smx_simcall_t simcall);
-void SIMIX_synchro_destroy(smx_synchro_t synchro);
-
-smx_mutex_t SIMIX_mutex_init(void);
-void SIMIX_mutex_destroy(smx_mutex_t mutex);
-int SIMIX_mutex_trylock(smx_mutex_t mutex, smx_process_t issuer);
-void SIMIX_mutex_unlock(smx_mutex_t mutex, smx_process_t issuer);
-
-smx_cond_t SIMIX_cond_init(void);
-void SIMIX_cond_destroy(smx_cond_t cond);
-void SIMIX_cond_signal(smx_cond_t cond);
-void SIMIX_cond_broadcast(smx_cond_t cond);
-
-smx_sem_t SIMIX_sem_init(unsigned int value);
-void SIMIX_sem_destroy(smx_sem_t sem);
-void SIMIX_sem_release(smx_sem_t sem);
-int SIMIX_sem_would_block(smx_sem_t sem);
-int SIMIX_sem_get_capacity(smx_sem_t sem);
+XBT_PRIVATE void SIMIX_post_synchro(smx_synchro_t synchro);
+XBT_PRIVATE void SIMIX_synchro_stop_waiting(smx_process_t process, smx_simcall_t simcall);
+XBT_PRIVATE void SIMIX_synchro_destroy(smx_synchro_t synchro);
+
+XBT_PRIVATE smx_mutex_t SIMIX_mutex_init(void);
+XBT_PRIVATE void SIMIX_mutex_destroy(smx_mutex_t mutex);
+XBT_PRIVATE int SIMIX_mutex_trylock(smx_mutex_t mutex, smx_process_t issuer);
+XBT_PRIVATE void SIMIX_mutex_unlock(smx_mutex_t mutex, smx_process_t issuer);
+
+XBT_PRIVATE smx_cond_t SIMIX_cond_init(void);
+XBT_PRIVATE void SIMIX_cond_destroy(smx_cond_t cond);
+XBT_PRIVATE void SIMIX_cond_broadcast(smx_cond_t cond);
+XBT_PRIVATE void SIMIX_cond_signal(smx_cond_t cond);
+
+XBT_PRIVATE void SIMIX_sem_destroy(smx_sem_t sem);
+XBT_PRIVATE XBT_PRIVATE smx_sem_t SIMIX_sem_init(unsigned int value);
+XBT_PRIVATE void SIMIX_sem_release(smx_sem_t sem);
+XBT_PRIVATE int SIMIX_sem_would_block(smx_sem_t sem);
+XBT_PRIVATE int SIMIX_sem_get_capacity(smx_sem_t sem);
 
 #endif
index 561e757..033cdb6 100644 (file)
@@ -140,7 +140,7 @@ int smpi_coll_tuned_gather_mvapich2_two_level(void *sendbuf,
     int leader_root, leader_of_root;
     MPI_Status status;
     MPI_Aint sendtype_extent = 0, recvtype_extent = 0;  /* Datatype extent */
-    MPI_Aint true_lb, sendtype_true_extent, recvtype_true_extent;
+    MPI_Aint true_lb = 0, sendtype_true_extent = 0, recvtype_true_extent = 0;
     MPI_Comm shmem_comm, leader_comm;
     void* tmp_buf = NULL;
     
index 2bc55d9..8844d20 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl
+#!/usr/bin/env perl
 
 # Copyright (c) 2011, 2014. The SimGrid Team.
 # All rights reserved.
index 00c8ed8..ce49def 100644 (file)
@@ -9,6 +9,7 @@
 
 #include "internal_config.h"
 #include "xbt.h"
+#include "xbt/base.h"
 #include "xbt/xbt_os_time.h"
 #include "xbt/synchro_core.h"
 #include "simgrid/simix.h"
@@ -130,11 +131,11 @@ typedef struct s_smpi_mpi_info {
 } s_smpi_mpi_info_t; 
 
 
-void smpi_process_destroy(void);
-void smpi_process_finalize(void);
-int smpi_process_finalized(void);
-int smpi_process_initialized(void);
-void smpi_process_mark_as_initialized(void);
+XBT_PRIVATE void smpi_process_destroy(void);
+XBT_PRIVATE void smpi_process_finalize(void);
+XBT_PRIVATE int smpi_process_finalized(void);
+XBT_PRIVATE int smpi_process_initialized(void);
+XBT_PRIVATE void smpi_process_mark_as_initialized(void);
 
 
 struct s_smpi_mpi_cart_topology;
@@ -148,327 +149,327 @@ typedef struct s_smpi_dist_graph_topology *MPIR_Dist_Graph_Topology;
 
 // MPI_Topology defined in smpi.h, as it is public
 
-void smpi_topo_destroy(MPI_Topology topo);
-MPI_Topology smpi_topo_create(MPIR_Topo_type kind);
-void smpi_cart_topo_destroy(MPIR_Cart_Topology cart);
-MPI_Topology smpi_cart_topo_create(int ndims);
-int smpi_mpi_cart_create(MPI_Comm comm_old, int ndims, int dims[],
+XBT_PRIVATE void smpi_topo_destroy(MPI_Topology topo);
+XBT_PRIVATE MPI_Topology smpi_topo_create(MPIR_Topo_type kind);
+XBT_PRIVATE void smpi_cart_topo_destroy(MPIR_Cart_Topology cart);
+XBT_PRIVATE MPI_Topology smpi_cart_topo_create(int ndims);
+XBT_PRIVATE int smpi_mpi_cart_create(MPI_Comm comm_old, int ndims, int dims[],
                          int periods[], int reorder, MPI_Comm *comm_cart);
-int smpi_mpi_cart_sub(MPI_Comm comm, const int remain_dims[], MPI_Comm *newcomm);
-int smpi_mpi_cart_coords(MPI_Comm comm, int rank, int maxdims,
+XBT_PRIVATE int smpi_mpi_cart_sub(MPI_Comm comm, const int remain_dims[], MPI_Comm *newcomm);
+XBT_PRIVATE int smpi_mpi_cart_coords(MPI_Comm comm, int rank, int maxdims,
                          int coords[]);
-int smpi_mpi_cart_get(MPI_Comm comm, int maxdims, int* dims, int* periods,
+XBT_PRIVATE int smpi_mpi_cart_get(MPI_Comm comm, int maxdims, int* dims, int* periods,
                       int* coords);
-int smpi_mpi_cart_rank(MPI_Comm comm, int* coords, int* rank);
-int smpi_mpi_cart_shift(MPI_Comm comm, int direction, int disp,
+XBT_PRIVATE int smpi_mpi_cart_rank(MPI_Comm comm, int* coords, int* rank);
+XBT_PRIVATE int smpi_mpi_cart_shift(MPI_Comm comm, int direction, int disp,
                         int *rank_source, int *rank_dest);
-int smpi_mpi_cartdim_get(MPI_Comm comm, int *ndims);
-int smpi_mpi_dims_create(int nnodes, int ndims, int dims[]);
-
-
-smpi_process_data_t smpi_process_data(void);
-smpi_process_data_t smpi_process_remote_data(int index);
-void smpi_process_set_user_data(void *);
-void* smpi_process_get_user_data(void);
-int smpi_process_count(void);
-MPI_Comm smpi_process_comm_world(void);
-MPI_Comm smpi_process_get_comm_intra(void);
-void smpi_process_set_comm_intra(MPI_Comm comm);
-smx_rdv_t smpi_process_mailbox(void);
-smx_rdv_t smpi_process_remote_mailbox(int index);
-smx_rdv_t smpi_process_mailbox_small(void);
-smx_rdv_t smpi_process_remote_mailbox_small(int index);
-xbt_mutex_t smpi_process_mailboxes_mutex(void);
-xbt_mutex_t smpi_process_remote_mailboxes_mutex(int index);
-xbt_os_timer_t smpi_process_timer(void);
-void smpi_process_simulated_start(void);
-double smpi_process_simulated_elapsed(void);
-void smpi_process_set_sampling(int s);
-int smpi_process_get_sampling(void);
-void smpi_process_set_replaying(int s);
-int smpi_process_get_replaying(void);
-
-void smpi_deployment_register_process(const char* instance_id, int rank, int index, MPI_Comm**, xbt_bar_t*);
-void smpi_deployment_cleanup_instances(void);
-
-void smpi_comm_copy_buffer_callback(smx_synchro_t comm,
+XBT_PRIVATE int smpi_mpi_cartdim_get(MPI_Comm comm, int *ndims);
+XBT_PRIVATE int smpi_mpi_dims_create(int nnodes, int ndims, int dims[]);
+
+
+XBT_PRIVATE smpi_process_data_t smpi_process_data(void);
+XBT_PRIVATE smpi_process_data_t smpi_process_remote_data(int index);
+XBT_PRIVATE void smpi_process_set_user_data(void *);
+XBT_PRIVATE void* smpi_process_get_user_data(void);
+XBT_PRIVATE int smpi_process_count(void);
+XBT_PRIVATE MPI_Comm smpi_process_comm_world(void);
+XBT_PRIVATE MPI_Comm smpi_process_get_comm_intra(void);
+XBT_PRIVATE void smpi_process_set_comm_intra(MPI_Comm comm);
+XBT_PRIVATE smx_rdv_t smpi_process_mailbox(void);
+XBT_PRIVATE smx_rdv_t smpi_process_remote_mailbox(int index);
+XBT_PRIVATE smx_rdv_t smpi_process_mailbox_small(void);
+XBT_PRIVATE smx_rdv_t smpi_process_remote_mailbox_small(int index);
+XBT_PRIVATE xbt_mutex_t smpi_process_mailboxes_mutex(void);
+XBT_PRIVATE xbt_mutex_t smpi_process_remote_mailboxes_mutex(int index);
+XBT_PRIVATE xbt_os_timer_t smpi_process_timer(void);
+XBT_PRIVATE void smpi_process_simulated_start(void);
+XBT_PRIVATE double smpi_process_simulated_elapsed(void);
+XBT_PRIVATE void smpi_process_set_sampling(int s);
+XBT_PRIVATE int smpi_process_get_sampling(void);
+XBT_PRIVATE void smpi_process_set_replaying(int s);
+XBT_PRIVATE int smpi_process_get_replaying(void);
+
+XBT_PRIVATE void smpi_deployment_register_process(const char* instance_id, int rank, int index, MPI_Comm**, xbt_bar_t*);
+XBT_PRIVATE void smpi_deployment_cleanup_instances(void);
+
+XBT_PRIVATE void smpi_comm_copy_buffer_callback(smx_synchro_t comm,
                                            void *buff, size_t buff_size);
 
-void smpi_comm_null_copy_buffer_callback(smx_synchro_t comm,
+XBT_PRIVATE void smpi_comm_null_copy_buffer_callback(smx_synchro_t comm,
                                            void *buff, size_t buff_size);
 
-void print_request(const char *message, MPI_Request request);
+XBT_PRIVATE void print_request(const char *message, MPI_Request request);
 
-int smpi_enabled(void);
-void smpi_global_init(void);
-void smpi_global_destroy(void);
-double smpi_mpi_wtime(void);
+XBT_PRIVATE int smpi_enabled(void);
+XBT_PRIVATE void smpi_global_init(void);
+XBT_PRIVATE void smpi_global_destroy(void);
+XBT_PRIVATE double smpi_mpi_wtime(void);
 
-int is_datatype_valid(MPI_Datatype datatype);
+XBT_PRIVATE int is_datatype_valid(MPI_Datatype datatype);
 
-size_t smpi_datatype_size(MPI_Datatype datatype);
-MPI_Aint smpi_datatype_lb(MPI_Datatype datatype);
-MPI_Aint smpi_datatype_ub(MPI_Datatype datatype);
-int smpi_datatype_dup(MPI_Datatype datatype, MPI_Datatype* new_t);
-int smpi_datatype_extent(MPI_Datatype datatype, MPI_Aint * lb,
+XBT_PRIVATE size_t smpi_datatype_size(MPI_Datatype datatype);
+XBT_PRIVATE MPI_Aint smpi_datatype_lb(MPI_Datatype datatype);
+XBT_PRIVATE MPI_Aint smpi_datatype_ub(MPI_Datatype datatype);
+XBT_PRIVATE int smpi_datatype_dup(MPI_Datatype datatype, MPI_Datatype* new_t);
+XBT_PRIVATE int smpi_datatype_extent(MPI_Datatype datatype, MPI_Aint * lb,
                          MPI_Aint * extent);
-MPI_Aint smpi_datatype_get_extent(MPI_Datatype datatype);
-void smpi_datatype_get_name(MPI_Datatype datatype, char* name, int* length);
-void smpi_datatype_set_name(MPI_Datatype datatype, char* name);
-int smpi_datatype_copy(void *sendbuf, int sendcount, MPI_Datatype sendtype,
+XBT_PRIVATE MPI_Aint smpi_datatype_get_extent(MPI_Datatype datatype);
+XBT_PRIVATE void smpi_datatype_get_name(MPI_Datatype datatype, char* name, int* length);
+XBT_PRIVATE void smpi_datatype_set_name(MPI_Datatype datatype, char* name);
+XBT_PRIVATE int smpi_datatype_copy(void *sendbuf, int sendcount, MPI_Datatype sendtype,
                        void *recvbuf, int recvcount,
                        MPI_Datatype recvtype);
-void smpi_datatype_use(MPI_Datatype type);
-void smpi_datatype_unuse(MPI_Datatype type);
+XBT_PRIVATE void smpi_datatype_use(MPI_Datatype type);
+XBT_PRIVATE void smpi_datatype_unuse(MPI_Datatype type);
 
-int smpi_datatype_contiguous(int count, MPI_Datatype old_type,
+XBT_PRIVATE int smpi_datatype_contiguous(int count, MPI_Datatype old_type,
                        MPI_Datatype* new_type, MPI_Aint lb);
-int smpi_datatype_vector(int count, int blocklen, int stride,
+XBT_PRIVATE int smpi_datatype_vector(int count, int blocklen, int stride,
                       MPI_Datatype old_type, MPI_Datatype* new_type);
 
-int smpi_datatype_hvector(int count, int blocklen, MPI_Aint stride,
+XBT_PRIVATE int smpi_datatype_hvector(int count, int blocklen, MPI_Aint stride,
                       MPI_Datatype old_type, MPI_Datatype* new_type);
-int smpi_datatype_indexed(int count, int* blocklens, int* indices,
+XBT_PRIVATE int smpi_datatype_indexed(int count, int* blocklens, int* indices,
                      MPI_Datatype old_type, MPI_Datatype* new_type);
-int smpi_datatype_hindexed(int count, int* blocklens, MPI_Aint* indices,
+XBT_PRIVATE int smpi_datatype_hindexed(int count, int* blocklens, MPI_Aint* indices,
                      MPI_Datatype old_type, MPI_Datatype* new_type);
-int smpi_datatype_struct(int count, int* blocklens, MPI_Aint* indices,
+XBT_PRIVATE int smpi_datatype_struct(int count, int* blocklens, MPI_Aint* indices,
                     MPI_Datatype* old_types, MPI_Datatype* new_type);
 
-void smpi_datatype_create(MPI_Datatype* new_type, int size,int lb, int ub, int has_subtype, void *struct_type, int flags);
+XBT_PRIVATE void smpi_datatype_create(MPI_Datatype* new_type, int size,int lb, int ub, int has_subtype, void *struct_type, int flags);
 
 
-void smpi_datatype_free(MPI_Datatype* type);
-void smpi_datatype_commit(MPI_Datatype* datatype);
+XBT_PRIVATE void smpi_datatype_free(MPI_Datatype* type);
+XBT_PRIVATE void smpi_datatype_commit(MPI_Datatype* datatype);
 
-int smpi_mpi_unpack(void* inbuf, int insize, int* position, void* outbuf, int outcount, MPI_Datatype type, MPI_Comm comm);
-int smpi_mpi_pack(void* inbuf, int incount, MPI_Datatype type, void* outbuf, int outcount, int* position, MPI_Comm comm);
+XBT_PRIVATE int smpi_mpi_unpack(void* inbuf, int insize, int* position, void* outbuf, int outcount, MPI_Datatype type, MPI_Comm comm);
+XBT_PRIVATE int smpi_mpi_pack(void* inbuf, int incount, MPI_Datatype type, void* outbuf, int outcount, int* position, MPI_Comm comm);
 
-void smpi_empty_status(MPI_Status * status);
-MPI_Op smpi_op_new(MPI_User_function * function, int commute);
-int smpi_op_is_commute(MPI_Op op);
-void smpi_op_destroy(MPI_Op op);
-void smpi_op_apply(MPI_Op op, void *invec, void *inoutvec, int *len,
+XBT_PRIVATE void smpi_empty_status(MPI_Status * status);
+XBT_PRIVATE MPI_Op smpi_op_new(MPI_User_function * function, int commute);
+XBT_PRIVATE int smpi_op_is_commute(MPI_Op op);
+XBT_PRIVATE void smpi_op_destroy(MPI_Op op);
+XBT_PRIVATE void smpi_op_apply(MPI_Op op, void *invec, void *inoutvec, int *len,
                    MPI_Datatype * datatype);
 
-MPI_Group smpi_group_new(int size);
-MPI_Group smpi_group_copy(MPI_Group origin);
-void smpi_group_destroy(MPI_Group group);
-void smpi_group_set_mapping(MPI_Group group, int index, int rank);
-int smpi_group_index(MPI_Group group, int rank);
-int smpi_group_rank(MPI_Group group, int index);
-int smpi_group_use(MPI_Group group);
-int smpi_group_unuse(MPI_Group group);
-int smpi_group_size(MPI_Group group);
-int smpi_group_compare(MPI_Group group1, MPI_Group group2);
-int smpi_group_incl(MPI_Group group, int n, int* ranks, MPI_Group* newgroup);
-
-
-MPI_Topology smpi_comm_topo(MPI_Comm comm);
-MPI_Comm smpi_comm_new(MPI_Group group, MPI_Topology topo);
-void smpi_comm_destroy(MPI_Comm comm);
-MPI_Group smpi_comm_group(MPI_Comm comm);
-int smpi_comm_size(MPI_Comm comm);
-void smpi_comm_get_name(MPI_Comm comm, char* name, int* len);
-int smpi_comm_rank(MPI_Comm comm);
-MPI_Comm smpi_comm_split(MPI_Comm comm, int color, int key);
-int smpi_comm_dup(MPI_Comm comm, MPI_Comm* newcomm);
-void smpi_comm_use(MPI_Comm comm);
-void smpi_comm_unuse(MPI_Comm comm);
-void smpi_comm_set_leaders_comm(MPI_Comm comm, MPI_Comm leaders);
-void smpi_comm_set_intra_comm(MPI_Comm comm, MPI_Comm leaders);
-int* smpi_comm_get_non_uniform_map(MPI_Comm comm);
-int* smpi_comm_get_leaders_map(MPI_Comm comm);
-MPI_Comm smpi_comm_get_leaders_comm(MPI_Comm comm);
-MPI_Comm smpi_comm_get_intra_comm(MPI_Comm comm);
-int smpi_comm_is_uniform(MPI_Comm comm);
-int smpi_comm_is_blocked(MPI_Comm comm);
-void smpi_comm_init_smp(MPI_Comm comm);
-
-int smpi_comm_c2f(MPI_Comm comm);
-MPI_Comm smpi_comm_f2c(int comm);
-int smpi_group_c2f(MPI_Group group);
-MPI_Group smpi_group_f2c(int group);
-int smpi_request_c2f(MPI_Request req);
-MPI_Request smpi_request_f2c(int req);
-int smpi_type_c2f(MPI_Datatype datatype);
-MPI_Datatype smpi_type_f2c(int datatype);
-int smpi_op_c2f(MPI_Op op);
-MPI_Op smpi_op_f2c(int op);
-int smpi_win_c2f(MPI_Win win);
-MPI_Win smpi_win_f2c(int win);
-int smpi_info_c2f(MPI_Info info);
-MPI_Info smpi_info_f2c(int info);
-
-MPI_Request smpi_mpi_send_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Group smpi_group_new(int size);
+XBT_PRIVATE MPI_Group smpi_group_copy(MPI_Group origin);
+XBT_PRIVATE void smpi_group_destroy(MPI_Group group);
+XBT_PRIVATE void smpi_group_set_mapping(MPI_Group group, int index, int rank);
+XBT_PRIVATE int smpi_group_index(MPI_Group group, int rank);
+XBT_PRIVATE int smpi_group_rank(MPI_Group group, int index);
+XBT_PRIVATE int smpi_group_use(MPI_Group group);
+XBT_PRIVATE int smpi_group_unuse(MPI_Group group);
+XBT_PRIVATE int smpi_group_size(MPI_Group group);
+XBT_PRIVATE int smpi_group_compare(MPI_Group group1, MPI_Group group2);
+XBT_PRIVATE int smpi_group_incl(MPI_Group group, int n, int* ranks, MPI_Group* newgroup);
+
+
+XBT_PRIVATE MPI_Topology smpi_comm_topo(MPI_Comm comm);
+XBT_PRIVATE MPI_Comm smpi_comm_new(MPI_Group group, MPI_Topology topo);
+XBT_PRIVATE void smpi_comm_destroy(MPI_Comm comm);
+XBT_PRIVATE MPI_Group smpi_comm_group(MPI_Comm comm);
+XBT_PRIVATE int smpi_comm_size(MPI_Comm comm);
+XBT_PRIVATE void smpi_comm_get_name(MPI_Comm comm, char* name, int* len);
+XBT_PRIVATE int smpi_comm_rank(MPI_Comm comm);
+XBT_PRIVATE MPI_Comm smpi_comm_split(MPI_Comm comm, int color, int key);
+XBT_PRIVATE int smpi_comm_dup(MPI_Comm comm, MPI_Comm* newcomm);
+XBT_PRIVATE void smpi_comm_use(MPI_Comm comm);
+XBT_PRIVATE void smpi_comm_unuse(MPI_Comm comm);
+XBT_PRIVATE void smpi_comm_set_leaders_comm(MPI_Comm comm, MPI_Comm leaders);
+XBT_PRIVATE void smpi_comm_set_intra_comm(MPI_Comm comm, MPI_Comm leaders);
+XBT_PRIVATE int* smpi_comm_get_non_uniform_map(MPI_Comm comm);
+XBT_PRIVATE int* smpi_comm_get_leaders_map(MPI_Comm comm);
+XBT_PRIVATE MPI_Comm smpi_comm_get_leaders_comm(MPI_Comm comm);
+XBT_PRIVATE MPI_Comm smpi_comm_get_intra_comm(MPI_Comm comm);
+XBT_PRIVATE int smpi_comm_is_uniform(MPI_Comm comm);
+XBT_PRIVATE int smpi_comm_is_blocked(MPI_Comm comm);
+XBT_PRIVATE void smpi_comm_init_smp(MPI_Comm comm);
+
+XBT_PRIVATE int smpi_comm_c2f(MPI_Comm comm);
+XBT_PRIVATE MPI_Comm smpi_comm_f2c(int comm);
+XBT_PRIVATE int smpi_group_c2f(MPI_Group group);
+XBT_PRIVATE MPI_Group smpi_group_f2c(int group);
+XBT_PRIVATE int smpi_request_c2f(MPI_Request req);
+XBT_PRIVATE MPI_Request smpi_request_f2c(int req);
+XBT_PRIVATE int smpi_type_c2f(MPI_Datatype datatype);
+XBT_PRIVATE MPI_Datatype smpi_type_f2c(int datatype);
+XBT_PRIVATE int smpi_op_c2f(MPI_Op op);
+XBT_PRIVATE MPI_Op smpi_op_f2c(int op);
+XBT_PRIVATE int smpi_win_c2f(MPI_Win win);
+XBT_PRIVATE MPI_Win smpi_win_f2c(int win);
+XBT_PRIVATE int smpi_info_c2f(MPI_Info info);
+XBT_PRIVATE MPI_Info smpi_info_f2c(int info);
+
+XBT_PRIVATE MPI_Request smpi_mpi_send_init(void *buf, int count, MPI_Datatype datatype,
                                int dst, int tag, MPI_Comm comm);
-MPI_Request smpi_mpi_recv_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_mpi_recv_init(void *buf, int count, MPI_Datatype datatype,
                                int src, int tag, MPI_Comm comm);
-MPI_Request smpi_mpi_ssend_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_mpi_ssend_init(void *buf, int count, MPI_Datatype datatype,
                                int dst, int tag, MPI_Comm comm);
-void smpi_mpi_start(MPI_Request request);
-void smpi_mpi_startall(int count, MPI_Request * requests);
-void smpi_mpi_request_free(MPI_Request * request);
-MPI_Request smpi_isend_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE void smpi_mpi_start(MPI_Request request);
+XBT_PRIVATE void smpi_mpi_startall(int count, MPI_Request * requests);
+XBT_PRIVATE void smpi_mpi_request_free(MPI_Request * request);
+XBT_PRIVATE MPI_Request smpi_isend_init(void *buf, int count, MPI_Datatype datatype,
                             int dst, int tag, MPI_Comm comm);
-MPI_Request smpi_mpi_isend(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_mpi_isend(void *buf, int count, MPI_Datatype datatype,
                            int dst, int tag, MPI_Comm comm);
-MPI_Request smpi_issend_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_issend_init(void *buf, int count, MPI_Datatype datatype,
                             int dst, int tag, MPI_Comm comm);
-MPI_Request smpi_mpi_issend(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_mpi_issend(void *buf, int count, MPI_Datatype datatype,
                            int dst, int tag, MPI_Comm comm);
-MPI_Request smpi_irecv_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_irecv_init(void *buf, int count, MPI_Datatype datatype,
                             int src, int tag, MPI_Comm comm);
-MPI_Request smpi_mpi_irecv(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_mpi_irecv(void *buf, int count, MPI_Datatype datatype,
                            int src, int tag, MPI_Comm comm);
-MPI_Request smpi_rma_send_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_rma_send_init(void *buf, int count, MPI_Datatype datatype,
                             int src, int dst, int tag, MPI_Comm comm, MPI_Op op);
-MPI_Request smpi_rma_recv_init(void *buf, int count, MPI_Datatype datatype,
+XBT_PRIVATE MPI_Request smpi_rma_recv_init(void *buf, int count, MPI_Datatype datatype,
                             int src, int dst, int tag, MPI_Comm comm, MPI_Op op);
-void smpi_mpi_recv(void *buf, int count, MPI_Datatype datatype, int src,
+XBT_PRIVATE void smpi_mpi_recv(void *buf, int count, MPI_Datatype datatype, int src,
                    int tag, MPI_Comm comm, MPI_Status * status);
-void smpi_mpi_send(void *buf, int count, MPI_Datatype datatype, int dst,
+XBT_PRIVATE void smpi_mpi_send(void *buf, int count, MPI_Datatype datatype, int dst,
                    int tag, MPI_Comm comm);
-void smpi_mpi_ssend(void *buf, int count, MPI_Datatype datatype, int dst,
+XBT_PRIVATE void smpi_mpi_ssend(void *buf, int count, MPI_Datatype datatype, int dst,
                    int tag, MPI_Comm comm);
-void smpi_mpi_sendrecv(void *sendbuf, int sendcount, MPI_Datatype sendtype,
+XBT_PRIVATE void smpi_mpi_sendrecv(void *sendbuf, int sendcount, MPI_Datatype sendtype,
                        int dst, int sendtag, void *recvbuf, int recvcount,
                        MPI_Datatype recvtype, int src, int recvtag,
                        MPI_Comm comm, MPI_Status * status);
-int smpi_mpi_test(MPI_Request * request, MPI_Status * status);
-int smpi_mpi_testany(int count, MPI_Request requests[], int *index,
+XBT_PRIVATE int smpi_mpi_test(MPI_Request * request, MPI_Status * status);
+XBT_PRIVATE int smpi_mpi_testany(int count, MPI_Request requests[], int *index,
                      MPI_Status * status);
-int smpi_mpi_testall(int count, MPI_Request requests[],
+XBT_PRIVATE int smpi_mpi_testall(int count, MPI_Request requests[],
                      MPI_Status status[]);
-void smpi_mpi_probe(int source, int tag, MPI_Comm comm, MPI_Status* status);
-void smpi_mpi_iprobe(int source, int tag, MPI_Comm comm, int* flag,
+XBT_PRIVATE void smpi_mpi_probe(int source, int tag, MPI_Comm comm, MPI_Status* status);
+XBT_PRIVATE void smpi_mpi_iprobe(int source, int tag, MPI_Comm comm, int* flag,
                     MPI_Status* status);
-int smpi_mpi_get_count(MPI_Status * status, MPI_Datatype datatype);
-void smpi_mpi_wait(MPI_Request * request, MPI_Status * status);
-int smpi_mpi_waitany(int count, MPI_Request requests[],
+XBT_PRIVATE int smpi_mpi_get_count(MPI_Status * status, MPI_Datatype datatype);
+XBT_PRIVATE void smpi_mpi_wait(MPI_Request * request, MPI_Status * status);
+XBT_PRIVATE int smpi_mpi_waitany(int count, MPI_Request requests[],
                      MPI_Status * status);
-int smpi_mpi_waitall(int count, MPI_Request requests[],
+XBT_PRIVATE int smpi_mpi_waitall(int count, MPI_Request requests[],
                       MPI_Status status[]);
-int smpi_mpi_waitsome(int incount, MPI_Request requests[], int *indices,
+XBT_PRIVATE int smpi_mpi_waitsome(int incount, MPI_Request requests[], int *indices,
                       MPI_Status status[]);
-int smpi_mpi_testsome(int incount, MPI_Request requests[], int *indices,
+XBT_PRIVATE int smpi_mpi_testsome(int incount, MPI_Request requests[], int *indices,
                       MPI_Status status[]);
-void smpi_mpi_bcast(void *buf, int count, MPI_Datatype datatype, int root,
+XBT_PRIVATE void smpi_mpi_bcast(void *buf, int count, MPI_Datatype datatype, int root,
                     MPI_Comm comm);
-void smpi_mpi_barrier(MPI_Comm comm);
-void smpi_mpi_gather(void *sendbuf, int sendcount, MPI_Datatype sendtype,
+XBT_PRIVATE void smpi_mpi_barrier(MPI_Comm comm);
+XBT_PRIVATE void smpi_mpi_gather(void *sendbuf, int sendcount, MPI_Datatype sendtype,
                      void *recvbuf, int recvcount, MPI_Datatype recvtype,
                      int root, MPI_Comm comm);
-void smpi_mpi_reduce_scatter(void *sendbuf, void *recvbuf, int *recvcounts,
+XBT_PRIVATE void smpi_mpi_reduce_scatter(void *sendbuf, void *recvbuf, int *recvcounts,
                        MPI_Datatype datatype, MPI_Op op, MPI_Comm comm);
-void smpi_mpi_gatherv(void *sendbuf, int sendcount, MPI_Datatype sendtype,
+XBT_PRIVATE void smpi_mpi_gatherv(void *sendbuf, int sendcount, MPI_Datatype sendtype,
                       void *recvbuf, int *recvcounts, int *displs,
                       MPI_Datatype recvtype, int root, MPI_Comm comm);
-void smpi_mpi_allgather(void *sendbuf, int sendcount,
+XBT_PRIVATE void smpi_mpi_allgather(void *sendbuf, int sendcount,
                         MPI_Datatype sendtype, void *recvbuf,
                         int recvcount, MPI_Datatype recvtype,
                         MPI_Comm comm);
-void smpi_mpi_allgatherv(void *sendbuf, int sendcount,
+XBT_PRIVATE void smpi_mpi_allgatherv(void *sendbuf, int sendcount,
                          MPI_Datatype sendtype, void *recvbuf,
                          int *recvcounts, int *displs,
                          MPI_Datatype recvtype, MPI_Comm comm);
-void smpi_mpi_scatter(void *sendbuf, int sendcount, MPI_Datatype sendtype,
+XBT_PRIVATE void smpi_mpi_scatter(void *sendbuf, int sendcount, MPI_Datatype sendtype,
                       void *recvbuf, int recvcount, MPI_Datatype recvtype,
                       int root, MPI_Comm comm);
-void smpi_mpi_scatterv(void *sendbuf, int *sendcounts, int *displs,
+XBT_PRIVATE void smpi_mpi_scatterv(void *sendbuf, int *sendcounts, int *displs,
                        MPI_Datatype sendtype, void *recvbuf, int recvcount,
                        MPI_Datatype recvtype, int root, MPI_Comm comm);
-void smpi_mpi_reduce(void *sendbuf, void *recvbuf, int count,
+XBT_PRIVATE void smpi_mpi_reduce(void *sendbuf, void *recvbuf, int count,
                      MPI_Datatype datatype, MPI_Op op, int root,
                      MPI_Comm comm);
-void smpi_mpi_allreduce(void *sendbuf, void *recvbuf, int count,
+XBT_PRIVATE void smpi_mpi_allreduce(void *sendbuf, void *recvbuf, int count,
                         MPI_Datatype datatype, MPI_Op op, MPI_Comm comm);
-void smpi_mpi_scan(void *sendbuf, void *recvbuf, int count,
+XBT_PRIVATE void smpi_mpi_scan(void *sendbuf, void *recvbuf, int count,
                    MPI_Datatype datatype, MPI_Op op, MPI_Comm comm);
-void smpi_mpi_exscan(void *sendbuf, void *recvbuf, int count,
+XBT_PRIVATE void smpi_mpi_exscan(void *sendbuf, void *recvbuf, int count,
                    MPI_Datatype datatype, MPI_Op op, MPI_Comm comm);
 
-int smpi_mpi_win_free( MPI_Win* win);
+XBT_PRIVATE int smpi_mpi_win_free( MPI_Win* win);
 
-MPI_Win smpi_mpi_win_create( void *base, MPI_Aint size, int disp_unit, MPI_Info info, MPI_Comm comm);
+XBT_PRIVATE MPI_Win smpi_mpi_win_create( void *base, MPI_Aint size, int disp_unit, MPI_Info info, MPI_Comm comm);
 
-void smpi_mpi_win_get_name(MPI_Win win, char* name, int* length);
-void smpi_mpi_win_get_group(MPI_Win win, MPI_Group* group);
-void smpi_mpi_win_set_name(MPI_Win win, char* name);
+XBT_PRIVATE void smpi_mpi_win_get_name(MPI_Win win, char* name, int* length);
+XBT_PRIVATE void smpi_mpi_win_get_group(MPI_Win win, MPI_Group* group);
+XBT_PRIVATE void smpi_mpi_win_set_name(MPI_Win win, char* name);
 
-int smpi_mpi_win_fence( int assert,  MPI_Win win);
+XBT_PRIVATE int smpi_mpi_win_fence( int assert,  MPI_Win win);
 
-int smpi_mpi_win_post(MPI_Group group, int assert, MPI_Win win);
-int smpi_mpi_win_start(MPI_Group group, int assert, MPI_Win win);
-int smpi_mpi_win_complete(MPI_Win win);
-int smpi_mpi_win_wait(MPI_Win win);
+XBT_PRIVATE int smpi_mpi_win_post(MPI_Group group, int assert, MPI_Win win);
+XBT_PRIVATE int smpi_mpi_win_start(MPI_Group group, int assert, MPI_Win win);
+XBT_PRIVATE int smpi_mpi_win_complete(MPI_Win win);
+XBT_PRIVATE int smpi_mpi_win_wait(MPI_Win win);
 
-int smpi_mpi_get( void *origin_addr, int origin_count, MPI_Datatype origin_datatype, int target_rank,
+XBT_PRIVATE int smpi_mpi_get( void *origin_addr, int origin_count, MPI_Datatype origin_datatype, int target_rank,
               MPI_Aint target_disp, int target_count, MPI_Datatype target_datatype, MPI_Win win);
-int smpi_mpi_put( void *origin_addr, int origin_count, MPI_Datatype origin_datatype, int target_rank,
+XBT_PRIVATE int smpi_mpi_put( void *origin_addr, int origin_count, MPI_Datatype origin_datatype, int target_rank,
               MPI_Aint target_disp, int target_count, MPI_Datatype target_datatype, MPI_Win win);
-int smpi_mpi_accumulate( void *origin_addr, int origin_count, MPI_Datatype origin_datatype, int target_rank,
+XBT_PRIVATE int smpi_mpi_accumulate( void *origin_addr, int origin_count, MPI_Datatype origin_datatype, int target_rank,
               MPI_Aint target_disp, int target_count, MPI_Datatype target_datatype, MPI_Op op, MPI_Win win);
 
-void nary_tree_bcast(void *buf, int count, MPI_Datatype datatype, int root,
+XBT_PRIVATE void nary_tree_bcast(void *buf, int count, MPI_Datatype datatype, int root,
                      MPI_Comm comm, int arity);
-void nary_tree_barrier(MPI_Comm comm, int arity);
+XBT_PRIVATE void nary_tree_barrier(MPI_Comm comm, int arity);
 
-int smpi_coll_tuned_alltoall_ompi2(void *sendbuf, int sendcount,
+XBT_PRIVATE int smpi_coll_tuned_alltoall_ompi2(void *sendbuf, int sendcount,
                                       MPI_Datatype sendtype, void *recvbuf,
                                       int recvcount, MPI_Datatype recvtype,
                                       MPI_Comm comm);
-int smpi_coll_tuned_alltoall_bruck(void *sendbuf, int sendcount,
+XBT_PRIVATE int smpi_coll_tuned_alltoall_bruck(void *sendbuf, int sendcount,
                                    MPI_Datatype sendtype, void *recvbuf,
                                    int recvcount, MPI_Datatype recvtype,
                                    MPI_Comm comm);
-int smpi_coll_tuned_alltoall_basic_linear(void *sendbuf, int sendcount,
+XBT_PRIVATE int smpi_coll_tuned_alltoall_basic_linear(void *sendbuf, int sendcount,
                                           MPI_Datatype sendtype,
                                           void *recvbuf, int recvcount,
                                           MPI_Datatype recvtype,
                                           MPI_Comm comm);
-int smpi_coll_basic_alltoallv(void *sendbuf, int *sendcounts,
+XBT_PRIVATE int smpi_coll_basic_alltoallv(void *sendbuf, int *sendcounts,
                               int *senddisps, MPI_Datatype sendtype,
                               void *recvbuf, int *recvcounts,
                               int *recvdisps, MPI_Datatype recvtype,
                               MPI_Comm comm);
                               
-int smpi_comm_keyval_create(MPI_Comm_copy_attr_function* copy_fn, MPI_Comm_delete_attr_function* delete_fn, int* keyval, void* extra_state);
-int smpi_comm_keyval_free(int* keyval);
-int smpi_comm_attr_delete(MPI_Comm comm, int keyval);
-int smpi_comm_attr_get(MPI_Comm comm, int keyval, void* attr_value, int* flag);
-int smpi_comm_attr_put(MPI_Comm comm, int keyval, void* attr_value);
-int smpi_type_attr_delete(MPI_Datatype type, int keyval);
-int smpi_type_attr_get(MPI_Datatype type, int keyval, void* attr_value, int* flag);
-int smpi_type_attr_put(MPI_Datatype type, int keyval, void* attr_value);
-int smpi_type_keyval_create(MPI_Type_copy_attr_function* copy_fn, MPI_Type_delete_attr_function* delete_fn, int* keyval, void* extra_state);
-int smpi_type_keyval_free(int* keyval);
+XBT_PRIVATE int smpi_comm_keyval_create(MPI_Comm_copy_attr_function* copy_fn, MPI_Comm_delete_attr_function* delete_fn, int* keyval, void* extra_state);
+XBT_PRIVATE int smpi_comm_keyval_free(int* keyval);
+XBT_PRIVATE int smpi_comm_attr_get(MPI_Comm comm, int keyval, void* attr_value, int* flag);
+XBT_PRIVATE int smpi_comm_attr_delete(MPI_Comm comm, int keyval);
+XBT_PRIVATE int smpi_comm_attr_put(MPI_Comm comm, int keyval, void* attr_value);
+XBT_PRIVATE int smpi_type_attr_delete(MPI_Datatype type, int keyval);
+XBT_PRIVATE int smpi_type_attr_get(MPI_Datatype type, int keyval, void* attr_value, int* flag);
+XBT_PRIVATE int smpi_type_attr_put(MPI_Datatype type, int keyval, void* attr_value);
+XBT_PRIVATE int smpi_type_keyval_create(MPI_Type_copy_attr_function* copy_fn, MPI_Type_delete_attr_function* delete_fn, int* keyval, void* extra_state);
+XBT_PRIVATE int smpi_type_keyval_free(int* keyval);
 // utilities
-extern double smpi_cpu_threshold;
-extern double smpi_running_power;
-extern int smpi_privatize_global_variables;
-extern char* smpi_start_data_exe; //start of the data+bss segment of the executable
-extern int smpi_size_data_exe; //size of the data+bss segment of the executable
+extern XBT_PRIVATE double smpi_cpu_threshold;
+extern XBT_PRIVATE double smpi_running_power;
+extern XBT_PRIVATE int smpi_privatize_global_variables;
+extern XBT_PRIVATE char* smpi_start_data_exe; //start of the data+bss segment of the executable
+extern XBT_PRIVATE int smpi_size_data_exe; //size of the data+bss segment of the executable
 
 
-void smpi_switch_data_segment(int dest);
-void smpi_really_switch_data_segment(int dest);
-int smpi_is_privatisation_file(char* file);
+XBT_PRIVATE void smpi_switch_data_segment(int dest);
+XBT_PRIVATE void smpi_really_switch_data_segment(int dest);
+XBT_PRIVATE int smpi_is_privatisation_file(char* file);
 
-void smpi_get_executable_global_size(void);
-void smpi_initialize_global_memory_segments(void);
-void smpi_destroy_global_memory_segments(void);
-void smpi_bench_destroy(void);
-void smpi_bench_begin(void);
-void smpi_bench_end(void);
+XBT_PRIVATE void smpi_get_executable_global_size(void);
+XBT_PRIVATE void smpi_initialize_global_memory_segments(void);
+XBT_PRIVATE void smpi_destroy_global_memory_segments(void);
+XBT_PRIVATE void smpi_bench_destroy(void);
+XBT_PRIVATE void smpi_bench_begin(void);
+XBT_PRIVATE void smpi_bench_end(void);
 
-void* smpi_get_tmp_sendbuffer(int size);
-void* smpi_get_tmp_recvbuffer(int size);
-void  smpi_free_tmp_buffer(void* buf);
+XBT_PRIVATE void* smpi_get_tmp_sendbuffer(int size);
+XBT_PRIVATE void* smpi_get_tmp_recvbuffer(int size);
+XBT_PRIVATE void  smpi_free_tmp_buffer(void* buf);
 
-int smpi_comm_attr_delete(MPI_Comm comm, int keyval);
-int smpi_comm_attr_get(MPI_Comm comm, int keyval, void* attr_value, int* flag);
-int smpi_comm_attr_put(MPI_Comm comm, int keyval, void* attr_value);
+XBT_PRIVATE int smpi_comm_attr_get(MPI_Comm comm, int keyval, void* attr_value, int* flag);
+XBT_PRIVATE XBT_PRIVATE int smpi_comm_attr_delete(MPI_Comm comm, int keyval);
+XBT_PRIVATE int smpi_comm_attr_put(MPI_Comm comm, int keyval, void* attr_value);
 
 
 
@@ -738,28 +739,28 @@ void mpi_comm_get_parent_ ( int*parent, int* ierr);
 
 /********** Tracing **********/
 /* from smpi_instr.c */
-void TRACE_internal_smpi_set_category (const char *category);
-const char *TRACE_internal_smpi_get_category (void);
-void TRACE_smpi_collective_in(int rank, int root, const char *operation, instr_extra_data extra);
-void TRACE_smpi_collective_out(int rank, int root, const char *operation);
-void TRACE_smpi_computing_init(int rank);
-void TRACE_smpi_computing_out(int rank);
-void TRACE_smpi_computing_in(int rank, instr_extra_data extra);
-void TRACE_smpi_sleeping_init(int rank);
-void TRACE_smpi_sleeping_out(int rank);
-void TRACE_smpi_sleeping_in(int rank, instr_extra_data extra);
-void TRACE_smpi_testing_out(int rank);
-void TRACE_smpi_testing_in(int rank, instr_extra_data extra);
-void TRACE_smpi_alloc(void);
-void TRACE_smpi_release(void);
-void TRACE_smpi_ptp_in(int rank, int src, int dst, const char *operation,  instr_extra_data extra);
-void TRACE_smpi_ptp_out(int rank, int src, int dst, const char *operation);
-void TRACE_smpi_send(int rank, int src, int dst, int size);
-void TRACE_smpi_recv(int rank, int src, int dst);
-void TRACE_smpi_init(int rank);
-void TRACE_smpi_finalize(int rank);
-
-const char* encode_datatype(MPI_Datatype datatype, int* known);
+XBT_PRIVATE void TRACE_internal_smpi_set_category (const char *category);
+XBT_PRIVATE const char *TRACE_internal_smpi_get_category (void);
+XBT_PRIVATE void TRACE_smpi_collective_in(int rank, int root, const char *operation, instr_extra_data extra);
+XBT_PRIVATE void TRACE_smpi_collective_out(int rank, int root, const char *operation);
+XBT_PRIVATE void TRACE_smpi_computing_init(int rank);
+XBT_PRIVATE void TRACE_smpi_computing_out(int rank);
+XBT_PRIVATE void TRACE_smpi_computing_in(int rank, instr_extra_data extra);
+XBT_PRIVATE void TRACE_smpi_sleeping_init(int rank);
+XBT_PRIVATE void TRACE_smpi_sleeping_out(int rank);
+XBT_PRIVATE void TRACE_smpi_sleeping_in(int rank, instr_extra_data extra);
+XBT_PRIVATE void TRACE_smpi_testing_out(int rank);
+XBT_PRIVATE void TRACE_smpi_testing_in(int rank, instr_extra_data extra);
+XBT_PRIVATE void TRACE_smpi_alloc(void);
+XBT_PRIVATE void TRACE_smpi_release(void);
+XBT_PRIVATE void TRACE_smpi_ptp_in(int rank, int src, int dst, const char *operation,  instr_extra_data extra);
+XBT_PRIVATE void TRACE_smpi_ptp_out(int rank, int src, int dst, const char *operation);
+XBT_PRIVATE void TRACE_smpi_send(int rank, int src, int dst, int size);
+XBT_PRIVATE void TRACE_smpi_recv(int rank, int src, int dst);
+XBT_PRIVATE void TRACE_smpi_init(int rank);
+XBT_PRIVATE void TRACE_smpi_finalize(int rank);
+
+XBT_PRIVATE const char* encode_datatype(MPI_Datatype datatype, int* known);
 
 // TODO, make this static and expose it more cleanly
 
@@ -768,11 +769,11 @@ typedef struct s_smpi_privatisation_region {
   int file_descriptor;
 } s_smpi_privatisation_region_t, *smpi_privatisation_region_t;
 
-extern smpi_privatisation_region_t smpi_privatisation_regions;
-extern int smpi_loaded_page;
-extern int smpi_universe_size;
+extern XBT_PRIVATE smpi_privatisation_region_t smpi_privatisation_regions;
+extern XBT_PRIVATE int smpi_loaded_page;
+extern XBT_PRIVATE int smpi_universe_size;
 
-int SIMIX_process_get_PID(smx_process_t self);
+XBT_PRIVATE int SIMIX_process_get_PID(smx_process_t self);
 
 static inline __attribute__ ((always_inline))
 int smpi_process_index_of_smx_process(smx_process_t process) {
index 61a3437..263b191 100644 (file)
@@ -676,7 +676,7 @@ int smpi_main(int (*realmain) (int argc, char *argv[]), int argc, char *argv[])
     xbt_os_walltimer_stop(global_timer);
     if (sg_cfg_get_boolean("smpi/display_timing")){
       double global_time = xbt_os_timer_elapsed(global_timer);
-      XBT_INFO("Simulated time: %g seconds. \n "
+      XBT_INFO("Simulated time: %g seconds. \n\n"
           "The simulation took %g seconds (after parsing and platform setup)\n"
           "%g seconds were actual computation of the application"
           , SIMIX_get_clock(), global_time , smpi_total_benched_time);
index c88b436..f0e612f 100644 (file)
@@ -9,6 +9,8 @@
 #ifndef SMPI_DT_PRIVATE_H
 #define SMPI_DT_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "private.h"
 
 #define DT_FLAG_DESTROYED     0x0001  /**< user destroyed but some other layers still have a reference */
@@ -98,115 +100,115 @@ typedef struct s_smpi_mpi_struct{
   Functions to handle serialization/unserialization of messages, 3 for each type of MPI_Type
   One for creating the substructure to handle, one for serialization, one for unserialization
 */
-void unserialize_contiguous( const void *contiguous_vector,
+XBT_PRIVATE void unserialize_contiguous( const void *contiguous_vector,
                          void *noncontiguous_vector,
                          int count,
                          void *type,
                          MPI_Op op);
 
-void serialize_contiguous( const void *noncontiguous_vector,
+XBT_PRIVATE void serialize_contiguous( const void *noncontiguous_vector,
                        void *contiguous_vector,
                        int count,
                        void *type);
 
-void free_contiguous(MPI_Datatype* type);
+XBT_PRIVATE void free_contiguous(MPI_Datatype* type);
 
-s_smpi_mpi_contiguous_t* smpi_datatype_contiguous_create( MPI_Aint lb,
+XBT_PRIVATE s_smpi_mpi_contiguous_t* smpi_datatype_contiguous_create( MPI_Aint lb,
                                                   int block_count,
                                                   MPI_Datatype old_type,
                                                   int size_oldtype);
                                                   
-void unserialize_vector( const void *contiguous_vector,
+XBT_PRIVATE void unserialize_vector( const void *contiguous_vector,
                          void *noncontiguous_vector,
                          int count,
                          void *type,
                          MPI_Op op);
 
-void serialize_vector( const void *noncontiguous_vector,
+XBT_PRIVATE void serialize_vector( const void *noncontiguous_vector,
                        void *contiguous_vector,
                        int count,
                        void *type);
 
-void free_vector(MPI_Datatype* type);
+XBT_PRIVATE void free_vector(MPI_Datatype* type);
 
-s_smpi_mpi_vector_t* smpi_datatype_vector_create( int block_stride,
+XBT_PRIVATE s_smpi_mpi_vector_t* smpi_datatype_vector_create( int block_stride,
                                                   int block_length,
                                                   int block_count,
                                                   MPI_Datatype old_type,
                                                   int size_oldtype);
 
-void unserialize_hvector( const void *contiguous_vector,
+XBT_PRIVATE void unserialize_hvector( const void *contiguous_vector,
                          void *noncontiguous_vector,
                          int count,
                          void *type,
                          MPI_Op op);
 
-void serialize_hvector( const void *noncontiguous_vector,
+XBT_PRIVATE void serialize_hvector( const void *noncontiguous_vector,
                        void *contiguous_vector,
                        int count,
                        void *type);
 
-void free_hvector(MPI_Datatype* type);
+XBT_PRIVATE void free_hvector(MPI_Datatype* type);
 
-s_smpi_mpi_hvector_t* smpi_datatype_hvector_create( MPI_Aint block_stride,
+XBT_PRIVATE s_smpi_mpi_hvector_t* smpi_datatype_hvector_create( MPI_Aint block_stride,
                                                   int block_length,
                                                   int block_count,
                                                   MPI_Datatype old_type,
                                                   int size_oldtype);
 
 
-void unserialize_indexed( const void *contiguous_indexed,
+XBT_PRIVATE void unserialize_indexed( const void *contiguous_indexed,
                          void *noncontiguous_indexed,
                          int count,
                          void *type,
                          MPI_Op op);
 
-void serialize_indexed( const void *noncontiguous_vector,
+XBT_PRIVATE void serialize_indexed( const void *noncontiguous_vector,
                        void *contiguous_vector,
                        int count,
                        void *type);
 
-void free_indexed(MPI_Datatype* type);
+XBT_PRIVATE void free_indexed(MPI_Datatype* type);
 
-s_smpi_mpi_indexed_t* smpi_datatype_indexed_create(int* block_lengths,
+XBT_PRIVATE s_smpi_mpi_indexed_t* smpi_datatype_indexed_create(int* block_lengths,
                                                   int* block_indices,
                                                   int block_count,
                                                   MPI_Datatype old_type,
                                                   int size_oldtype);
 
-void unserialize_hindexed( const void *contiguous_indexed,
+XBT_PRIVATE void unserialize_hindexed( const void *contiguous_indexed,
                          void *noncontiguous_indexed,
                          int count,
                          void *type,
                          MPI_Op op);
 
-void serialize_hindexed( const void *noncontiguous_vector,
+XBT_PRIVATE void serialize_hindexed( const void *noncontiguous_vector,
                        void *contiguous_vector,
                        int count,
                        void *type);
 
-void free_hindexed(MPI_Datatype* type);
+XBT_PRIVATE void free_hindexed(MPI_Datatype* type);
 
-s_smpi_mpi_hindexed_t* smpi_datatype_hindexed_create(int* block_lengths,
+XBT_PRIVATE s_smpi_mpi_hindexed_t* smpi_datatype_hindexed_create(int* block_lengths,
                                                   MPI_Aint* block_indices,
                                                   int block_count,
                                                   MPI_Datatype old_type,
                                                   int size_oldtype);
 
-void unserialize_struct( const void *contiguous_indexed,
+XBT_PRIVATE void unserialize_struct( const void *contiguous_indexed,
                          void *noncontiguous_indexed,
                          int count,
                          void *type,
                          MPI_Op op);
 
-void serialize_struct( const void *noncontiguous_vector,
+XBT_PRIVATE void serialize_struct( const void *noncontiguous_vector,
                        void *contiguous_vector,
                        int count,
                        void *type);
 
-void free_struct(MPI_Datatype* type);
+XBT_PRIVATE void free_struct(MPI_Datatype* type);
 
-s_smpi_mpi_struct_t* smpi_datatype_struct_create(int* block_lengths,
+XBT_PRIVATE s_smpi_mpi_struct_t* smpi_datatype_struct_create(int* block_lengths,
                                                   MPI_Aint* block_indices,
                                                   int block_count,
                                                   MPI_Datatype* old_types);
index 9ab2b6d..99fdf8a 100644 (file)
@@ -1171,7 +1171,9 @@ int PMPI_Recv(void *buf, int count, MPI_Datatype datatype, int src, int tag,
   //the src may not have been known at the beginning of the recv (MPI_ANY_SOURCE)
   if(status!=MPI_STATUS_IGNORE){
     src_traced = smpi_group_index(smpi_comm_group(comm), status->MPI_SOURCE);
-    TRACE_smpi_recv(rank, src_traced, rank);
+    if (!TRACE_smpi_view_internals()) {
+      TRACE_smpi_recv(rank, src_traced, rank);
+    }
   }
   TRACE_smpi_ptp_out(rank, src_traced, rank, __FUNCTION__);
   }
@@ -1216,7 +1218,9 @@ int PMPI_Send(void *buf, int count, MPI_Datatype datatype, int dst, int tag,
     dt_size_send = smpi_datatype_size(datatype);
   extra->send_size = count*dt_size_send;
   TRACE_smpi_ptp_in(rank, rank, dst_traced, __FUNCTION__, extra);
-  TRACE_smpi_send(rank, rank, dst_traced,count*smpi_datatype_size(datatype));
+  if (!TRACE_smpi_view_internals()) {
+    TRACE_smpi_send(rank, rank, dst_traced,count*smpi_datatype_size(datatype));
+  }
 
     smpi_mpi_send(buf, count, datatype, dst, tag, comm);
     retval = MPI_SUCCESS;
index ae9e0a2..e543313 100644 (file)
@@ -263,7 +263,9 @@ static void action_send(const char *const *action)
   extra->dst = dst_traced;
   extra->datatype1 = encode_datatype(MPI_CURRENT_TYPE, NULL);
   TRACE_smpi_ptp_in(rank, rank, dst_traced, __FUNCTION__, extra);
-  TRACE_smpi_send(rank, rank, dst_traced, size*smpi_datatype_size(MPI_CURRENT_TYPE));
+  if (!TRACE_smpi_view_internals()) {
+    TRACE_smpi_send(rank, rank, dst_traced, size*smpi_datatype_size(MPI_CURRENT_TYPE));
+  }
 
   smpi_mpi_send(NULL, size, MPI_CURRENT_TYPE, to , 0, MPI_COMM_WORLD);
 
@@ -292,7 +294,9 @@ static void action_Isend(const char *const *action)
   extra->dst = dst_traced;
   extra->datatype1 = encode_datatype(MPI_CURRENT_TYPE, NULL);
   TRACE_smpi_ptp_in(rank, rank, dst_traced, __FUNCTION__, extra);
-  TRACE_smpi_send(rank, rank, dst_traced, size*smpi_datatype_size(MPI_CURRENT_TYPE));
+  if (!TRACE_smpi_view_internals()) {
+    TRACE_smpi_send(rank, rank, dst_traced, size*smpi_datatype_size(MPI_CURRENT_TYPE));
+  }
 
   request = smpi_mpi_isend(NULL, size, MPI_CURRENT_TYPE, to, 0,MPI_COMM_WORLD);
 
@@ -334,7 +338,9 @@ static void action_recv(const char *const *action) {
   smpi_mpi_recv(NULL, size, MPI_CURRENT_TYPE, from, 0, MPI_COMM_WORLD, &status);
 
   TRACE_smpi_ptp_out(rank, src_traced, rank, __FUNCTION__);
-  TRACE_smpi_recv(rank, src_traced, rank);
+  if (!TRACE_smpi_view_internals()) {
+    TRACE_smpi_recv(rank, src_traced, rank);
+  }
 
   log_timed_action (action, clock);
 }
index f27daa8..1d80693 100755 (executable)
@@ -511,10 +511,10 @@ export SMPI_GLOBAL_SIZE=${NUMPROCS}
 if [ -n "${KEEP}" ] ; then
     echo ${EXEC} ${TRACEOPTIONS} ${SIMOPTS} ${PLATFORMTMP} ${APPLICATIONTMP}
     if [ ${HOSTFILETMP} = 1 ] ; then
-        echo "Generated hostfile ${HOSTFILE} keeped."
+        echo "Generated hostfile ${HOSTFILE} kept."
     fi
     if [ ${UNROLLEDHOSTFILETMP} = 1 ] ; then
-        echo "Generated unrolled hostfile ${UNROLLEDHOSTFILE} keeped." 
+        echo "Generated unrolled hostfile ${UNROLLEDHOSTFILE} kept." 
     fi
 fi
 if [ "$foreground" = 1 ]; then
index a0aa210..316df92 100644 (file)
@@ -4,14 +4,16 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "cpu_interface.hpp"
 
 /***********
  * Classes *
  ***********/
-class CpuCas01Model;
-class CpuCas01;
-class CpuCas01Action;
+class XBT_PRIVATE CpuCas01Model;
+class XBT_PRIVATE CpuCas01;
+class XBT_PRIVATE CpuCas01Action;
 
 /*********
  * Model *
index 2edf742..00346bf 100644 (file)
@@ -836,11 +836,11 @@ CpuAction *CpuTi::sleep(double duration)
 void CpuTi::modified(bool modified){
   CpuTiList *modifiedCpu = static_cast<CpuTiModel*>(getModel())->p_modifiedCpu;
   if (modified) {
-    if (!is_linked()) {
+    if (!cpu_ti_hook.is_linked()) {
       modifiedCpu->push_back(*this);
     }
   } else {
-    if (is_linked()) {
+    if (cpu_ti_hook.is_linked()) {
       modifiedCpu->erase(modifiedCpu->iterator_to(*this));
     }
   }
@@ -881,10 +881,10 @@ int CpuTiAction::unref()
 {
   m_refcount--;
   if (!m_refcount) {
-       if (actionHook::is_linked())
+       if (action_hook.is_linked())
          getStateSet()->erase(getStateSet()->iterator_to(*this));
     /* remove from action_set */
-    if (actionTiHook::is_linked())
+    if (action_ti_hook.is_linked())
       p_cpu->p_actionSet->erase(p_cpu->p_actionSet->iterator_to(*this));
     /* remove from heap */
     xbt_heap_remove(static_cast<CpuTiModel*>(getModel())->p_tiActionHeap, this->m_indexHeap);
index 0841580..cf4016b 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "cpu_interface.hpp"
 #include "trace_mgr_private.h"
 #include "surf/surf_routing.h"
 /***********
  * Classes *
  ***********/
-class CpuTiTrace;
-class CpuTiTgmr;
-class CpuTiModel;
-class CpuTi;
-class CpuTiAction;
-
-typedef boost::intrusive::list<CpuTi> CpuTiList;
-typedef boost::intrusive::list_base_hook<> cpuTiHook;
+class XBT_PRIVATE CpuTiTrace;
+class XBT_PRIVATE CpuTiTgmr;
+class XBT_PRIVATE CpuTiModel;
+class XBT_PRIVATE CpuTi;
+class XBT_PRIVATE CpuTiAction;
 
 struct tiTag;
-typedef boost::intrusive::list<CpuTiAction, boost::intrusive::base_hook<boost::intrusive::list_base_hook<boost::intrusive::tag<tiTag> > > > ActionTiList;
-typedef boost::intrusive::list_base_hook<boost::intrusive::tag<tiTag> > actionTiHook;
 
 /*********
  * Trace *
@@ -75,40 +72,48 @@ public:
   tmgr_trace_t p_powerTrace;
 };
 
-/*********
- * Model *
- *********/
-class CpuTiModel : public CpuModel {
-public:
-  CpuTiModel();
-  ~CpuTiModel();
-  Cpu *createCpu(const char *name,  xbt_dynar_t powerPeak,
-                          int pstate, double power_scale,
-                          tmgr_trace_t power_trace, int core,
-                          e_surf_resource_state_t state_initial,
-                          tmgr_trace_t state_trace,
-                          xbt_dict_t cpu_properties);
-  double shareResources(double now);
-  void updateActionsState(double now, double delta);
-  void addTraces();
+/**********
+ * Action *
+ **********/
 
-  ActionList *p_runningActionSetThatDoesNotNeedBeingChecked;
-  CpuTiList *p_modifiedCpu;
-  xbt_heap_t p_tiActionHeap;
+class CpuTiAction: public CpuAction {
+  friend class CpuTi;
+  // friend CpuAction *CpuTi::execute(double size);
+  // friend CpuAction *CpuTi::sleep(double duration);
+  // friend void CpuTi::updateActionsFinishTime(double now);//FIXME
+  // friend void CpuTi::updateRemainingAmount(double now);//FIXME
+public:
+  CpuTiAction(CpuTiModel *model, double cost, bool failed,
+                   CpuTi *cpu);
 
-protected:
-  void NotifyResourceTurnedOn(Resource*){};
-  void NotifyResourceTurnedOff(Resource*){};
+  void setState(e_surf_action_state_t state);
+  int unref();
+  void cancel();
+  void updateIndexHeap(int i);
+  void suspend();
+  void resume();
+  bool isSuspended();
+  void setMaxDuration(double duration);
+  void setPriority(double priority);
+  double getRemains();
+  void setAffinity(Cpu * /*cpu*/, unsigned long /*mask*/) {};
 
-  void NotifyActionCancel(Action*){};
-  void NotifyActionResume(Action*){};
-  void NotifyActionSuspend(Action*){};
+  CpuTi *p_cpu;
+  int m_indexHeap;
+  int m_suspended;
+public:
+  boost::intrusive::list_member_hook<> action_ti_hook;
 };
 
+typedef boost::intrusive::member_hook<
+  CpuTiAction, boost::intrusive::list_member_hook<>, &CpuTiAction::action_ti_hook> ActionTiListOptions;
+typedef boost::intrusive::list<
+  CpuTiAction, ActionTiListOptions > ActionTiList;
+
 /************
  * Resource *
  ************/
-class CpuTi : public cpuTiHook, public Cpu {
+class CpuTi : public Cpu {
 public:
   CpuTi() {};
   CpuTi(CpuTiModel *model, const char *name, xbt_dynar_t powerPeak,
@@ -142,36 +147,40 @@ public:
   double current_frequency;
 
   void updateRemainingAmount(double now);
+public:
+  boost::intrusive::list_member_hook<> cpu_ti_hook;
 };
 
-/**********
- * Action *
- **********/
-
-class CpuTiAction: public actionTiHook, public CpuAction {
-  friend CpuAction *CpuTi::execute(double size);
-  friend CpuAction *CpuTi::sleep(double duration);
-  friend void CpuTi::updateActionsFinishTime(double now);//FIXME
-  friend void CpuTi::updateRemainingAmount(double now);//FIXME
+typedef boost::intrusive::member_hook<
+  CpuTi, boost::intrusive::list_member_hook<>, &CpuTi::cpu_ti_hook> CpuTiListOptions;
+typedef boost::intrusive::list<CpuTi, CpuTiListOptions> CpuTiList;
 
+/*********
+ * Model *
+ *********/
+class CpuTiModel : public CpuModel {
 public:
-  CpuTiAction(CpuTiModel *model, double cost, bool failed,
-                                CpuTi *cpu);
+  CpuTiModel();
+  ~CpuTiModel();
+  Cpu *createCpu(const char *name,  xbt_dynar_t powerPeak,
+                          int pstate, double power_scale,
+                          tmgr_trace_t power_trace, int core,
+                          e_surf_resource_state_t state_initial,
+                          tmgr_trace_t state_trace,
+                          xbt_dict_t cpu_properties);
+  double shareResources(double now);
+  void updateActionsState(double now, double delta);
+  void addTraces();
 
-  void setState(e_surf_action_state_t state);
-  int unref();
-  void cancel();
-  void updateIndexHeap(int i);
-  void suspend();
-  void resume();
-  bool isSuspended();
-  void setMaxDuration(double duration);
-  void setPriority(double priority);
-  double getRemains();
-  void setAffinity(Cpu */*cpu*/, unsigned long /*mask*/) {};
+  ActionList *p_runningActionSetThatDoesNotNeedBeingChecked;
+  CpuTiList *p_modifiedCpu;
+  xbt_heap_t p_tiActionHeap;
 
-  CpuTi *p_cpu;
-  int m_indexHeap;
-  int m_suspended;
-private:
+protected:
+  void NotifyResourceTurnedOn(Resource*){};
+  void NotifyResourceTurnedOff(Resource*){};
+
+  void NotifyActionCancel(Action*){};
+  void NotifyActionResume(Action*){};
+  void NotifyActionSuspend(Action*){};
 };
index 6018af2..e2d27bb 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "storage_interface.hpp"
 #include "cpu_interface.hpp"
 #include "host_interface.hpp"
@@ -16,9 +18,9 @@
  * Classes *
  ***********/
 
-class HostCLM03Model;
-class HostCLM03;
-class HostCLM03Action;
+class XBT_PRIVATE HostCLM03Model;
+class XBT_PRIVATE HostCLM03;
+class XBT_PRIVATE HostCLM03Action;
 
 /*********
  * Model *
index 759cb27..39e8780 100644 (file)
@@ -9,6 +9,8 @@
 #include "cpu_interface.hpp"
 #include "network_interface.hpp"
 
+#include <xbt/base.h>
+
 #ifndef SURF_HOST_INTERFACE_HPP_
 #define SURF_HOST_INTERFACE_HPP_
 
@@ -16,9 +18,9 @@
  * Classes *
  ***********/
 
-class HostModel;
-class Host;
-class HostAction;
+class XBT_PRIVATE HostModel;
+class XBT_PRIVATE Host;
+class XBT_PRIVATE HostAction;
 
 /*************
  * Callbacks *
index 40dc03f..39a6de1 100644 (file)
@@ -656,7 +656,7 @@ int L07Action::unref()
 {
   m_refcount--;
   if (!m_refcount) {
-    if (actionHook::is_linked())
+    if (action_hook.is_linked())
          p_stateSet->erase(p_stateSet->iterator_to(*this));
     if (getVariable())
       lmm_variable_free(ptask_maxmin_system, getVariable());
index d3466c9..51dd683 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "host_interface.hpp"
 
 #ifndef HOST_L07_HPP_
  * Classes *
  ***********/
 
-class HostL07Model;
-class CpuL07Model;
-class NetworkL07Model;
+class XBT_PRIVATE HostL07Model;
+class XBT_PRIVATE CpuL07Model;
+class XBT_PRIVATE NetworkL07Model;
 
-class HostL07;
-class CpuL07;
-class LinkL07;
+class XBT_PRIVATE HostL07;
+class XBT_PRIVATE CpuL07;
+class XBT_PRIVATE LinkL07;
 
-class L07Action;
+class XBT_PRIVATE L07Action;
 
 /*********
  * Tools *
index 2ed593c..a060d6b 100644 (file)
@@ -20,8 +20,8 @@ typedef struct s_dyn_light {
   int size;
 } s_dyn_light_t, *dyn_light_t;
 
-XBT_EXPORT_NO_IMPORT(double) sg_maxmin_precision = 0.00001;
-XBT_EXPORT_NO_IMPORT(double) sg_surf_precision   = 0.00001;
+double sg_maxmin_precision = 0.00001;
+double sg_surf_precision   = 0.00001;
 
 static void *lmm_variable_mallocator_new_f(void);
 static void lmm_variable_mallocator_free_f(void *var);
index d3ab7f9..48479c8 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _SURF_MAXMIN_PRIVATE_H
 #define _SURF_MAXMIN_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "surf/maxmin.h"
 #include "xbt/swag.h"
 #include "xbt/mallocator.h"
@@ -119,10 +121,10 @@ typedef struct lmm_system {
  * 
  * @param sys A lmm system
  */
-void lmm_print(lmm_system_t sys);
+XBT_PRIVATE void lmm_print(lmm_system_t sys);
 
-extern double (*func_f_def) (lmm_variable_t, double);
-extern double (*func_fp_def) (lmm_variable_t, double);
-extern double (*func_fpi_def) (lmm_variable_t, double);
+extern XBT_PRIVATE double (*func_f_def) (lmm_variable_t, double);
+extern XBT_PRIVATE double (*func_fp_def) (lmm_variable_t, double);
+extern XBT_PRIVATE double (*func_fpi_def) (lmm_variable_t, double);
 
 #endif                          /* _SURF_MAXMIN_PRIVATE_H */
index f384e5f..888907d 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef SURF_NETWORK_CM02_HPP_
 #define SURF_NETWORK_CM02_HPP_
 
+#include <xbt/base.h>
+
 #include "network_interface.hpp"
 #include "xbt/fifo.h"
 #include "xbt/graph.h"
 /***********
  * Classes *
  ***********/
-class NetworkCm02Model;
-class NetworkCm02Action;
+class XBT_PRIVATE NetworkCm02Model;
+class XBT_PRIVATE NetworkCm02Action;
 
 /*********
  * Tools *
  *********/
 
-void net_define_callbacks(void);
+XBT_PRIVATE void net_define_callbacks(void);
 
 /*********
  * Model *
index 9461678..3421c67 100644 (file)
@@ -103,7 +103,7 @@ int NetworkConstantAction::unref()
 {
   m_refcount--;
   if (!m_refcount) {
-       if (actionHook::is_linked())
+       if (action_hook.is_linked())
          p_stateSet->erase(p_stateSet->iterator_to(*this));
     delete this;
   return 1;
@@ -116,7 +116,7 @@ void NetworkConstantAction::cancel()
   return;
 }
 
-void NetworkConstantAction::setCategory(const char */*category*/)
+void NetworkConstantAction::setCategory(const char * /*category*/)
 {
   //ignore completely the categories in constant model, they are not traced
 }
index 2dc6681..ad40084 100644 (file)
@@ -7,13 +7,15 @@
 #ifndef NETWORK_CONSTANT_HPP_
 #define NETWORK_CONSTANT_HPP_
 
+#include <xbt/base.h>
+
 #include "network_interface.hpp"
 
 /***********
  * Classes *
  ***********/
-class NetworkConstantModel;
-class NetworkConstantAction;
+class XBT_PRIVATE NetworkConstantModel;
+class XBT_PRIVATE NetworkConstantAction;
 
 /*********
  * Model *
index 4c39884..26a27ea 100644 (file)
@@ -7,11 +7,12 @@
 #ifndef SURF_NETWORK_IB_HPP_
 #define SURF_NETWORK_IB_HPP_
 
-#include "network_smpi.hpp"
-class IBNode;
+#include <xbt/base.h>
 
+#include "network_smpi.hpp"
+class XBT_PRIVATE IBNode;
 
-class ActiveComm{
+class XBT_PRIVATE ActiveComm{
 public :
   //IBNode* origin;
   IBNode* destination;
@@ -34,7 +35,7 @@ public :
   ~IBNode(){};
 };
 
-class NetworkIBModel : public NetworkSmpiModel {
+class XBT_PRIVATE NetworkIBModel : public NetworkSmpiModel {
 private:
   void updateIBfactors_rec(IBNode *root, bool* updatedlist);
   void computeIBfactors(IBNode *root);
index 9fd4ccc..c9de3c5 100644 (file)
@@ -79,6 +79,7 @@ Link **Link::linksList() {
 void Link::linksExit() {
        for (auto kv : *links)
                delete (kv.second);
+       delete links;
 }
 /*************
  * Callbacks *
index ae9ce5d..bca2f83 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef SURF_NETWORK_INTERFACE_HPP_
 #define SURF_NETWORK_INTERFACE_HPP_
 
+#include <xbt/base.h>
+
 #include <boost/unordered_map.hpp>
 
 #include "xbt/fifo.h"
@@ -109,7 +111,7 @@ public:
                                    e_surf_link_sharing_policy_t policy,
                                    xbt_dict_t properties)=0;
 
-  virtual void gapAppend(double /*size*/, const Link* /*link*/, NetworkAction */*action*/) {};
+  virtual void gapAppend(double /*size*/, const Link* /*link*/, NetworkAction * /*action*/) {};
 
   /**
    * @brief Create a communication between two hosts.
index 417b15b..f452d94 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "network_interface.hpp"
 #include "surf/ns3/ns3_interface.h"
 
 /***********
  * Classes *
  ***********/
-class NetworkNS3Model;
-class NetworkNS3Action;
+class XBT_PRIVATE NetworkNS3Model;
+class XBT_PRIVATE NetworkNS3Action;
 
 /*********
  * Tools *
  *********/
 
-void net_define_callbacks(void);
+XBT_PRIVATE void net_define_callbacks(void);
 
 /*********
  * Model *
index a8dd24c..ddbfd25 100644 (file)
@@ -4,13 +4,15 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "network_cm02.hpp"
 
 /***********
  * Classes *
  ***********/
 
-class NetworkSmpiModel;
+class XBT_PRIVATE NetworkSmpiModel;
 
 /*********
  * Tools *
index 9b04b44..ea57365 100644 (file)
@@ -7,15 +7,17 @@
 #ifndef SG_PLATF_GEN_PRIVATE_H
 #define SG_PLATF_GEN_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "xbt/graph.h"
 #include "simgrid/platf.h"
 
-void platf_graph_init(unsigned long node_count);
+XBT_PRIVATE void platf_graph_init(unsigned long node_count);
 
-void platf_node_connect(xbt_node_t node1, xbt_node_t node2);
+XBT_PRIVATE void platf_node_connect(xbt_node_t node1, xbt_node_t node2);
 
-double platf_node_distance(xbt_node_t node1, xbt_node_t node2);
+XBT_PRIVATE double platf_node_distance(xbt_node_t node1, xbt_node_t node2);
 
-double random_pareto(double min, double max, double K, double P, double ALPHA);
+XBT_PRIVATE double random_pareto(double min, double max, double K, double P, double ALPHA);
 
 #endif      /* SG_PLATF_GEN_PRIVATE_H */
index 8be8068..ca80808 100644 (file)
@@ -144,8 +144,8 @@ void sg_energy_plugin_init() {
  *
  */
 CpuEnergy::CpuEnergy(Cpu *ptr)
- : cpu(ptr)
 {
+  cpu = ptr;
   total_energy = 0;
   power_range_watts_list = getWattsRangeList();
   last_updated = surf_get_clock();
index 8f8d5bd..ab9d1f3 100644 (file)
@@ -4,15 +4,17 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "../cpu_interface.hpp"
 #include <map>
 
 #ifndef CALLBACK_HPP_
 #define CALLBACK_HPP_
 
-class CpuEnergy;
+class XBT_PRIVATE CpuEnergy;
 
-extern std::map<Cpu*, CpuEnergy*> *surf_energy;
+extern XBT_PRIVATE std::map<Cpu*, CpuEnergy*> *surf_energy;
 
 class CpuEnergy {
 public:
index 5718a00..073a6ef 100644 (file)
@@ -6,6 +6,7 @@
 
 #include "storage_interface.hpp"
 #include "surf_private.h"
+#include "xbt/file.h" /* xbt_getline */
 
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(surf_storage, surf,
                                 "Logging specific to the SURF storage module");
index f5debbd..fe0c0d4 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "surf_interface.hpp"
 
 #ifndef STORAGE_INTERFACE_HPP_
index 7d73325..42fef37 100644 (file)
@@ -433,7 +433,11 @@ StorageAction *StorageN11::close(surf_file_t fd)
 StorageAction *StorageN11::read(surf_file_t fd, sg_size_t size)
 {
   if(fd->current_position + size > fd->size){
-    size = fd->size - fd->current_position;
+    if (fd->current_position > fd->size){
+      size = 0;
+    } else {
+      size = fd->size - fd->current_position;
+    }
     fd->current_position = fd->size;
   }
   else
@@ -498,7 +502,7 @@ int StorageN11Action::unref()
 {
   m_refcount--;
   if (!m_refcount) {
-       if (actionHook::is_linked())
+       if (action_hook.is_linked())
          p_stateSet->erase(p_stateSet->iterator_to(*this));
     if (getVariable())
       lmm_variable_free(getModel()->getMaxminSystem(), getVariable());
index d95155e..9cb4522 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "storage_interface.hpp"
 
 #ifndef STORAGE_N11_HPP_
@@ -13,9 +15,9 @@
  * Classes *
  ***********/
 
-class StorageN11Model;
-class StorageN11;
-class StorageN11Action;
+class XBT_PRIVATE StorageN11Model;
+class XBT_PRIVATE StorageN11;
+class XBT_PRIVATE StorageN11Action;
 
 /*********
  * Model *
index 5cf6362..8c78bcc 100644 (file)
@@ -871,7 +871,7 @@ void Action::setPriority(double priority)
 void Action::cancel(){
   setState(SURF_ACTION_FAILED);
   if (getModel()->getUpdateMechanism() == UM_LAZY) {
-    if (actionLmmHook::is_linked())
+    if (action_lmm_hook.is_linked())
       getModel()->getModifiedSet()->erase(getModel()->getModifiedSet()->iterator_to(*this));
     heapRemove(getModel()->getActionHeap());
   }
@@ -880,14 +880,14 @@ void Action::cancel(){
 int Action::unref(){
   m_refcount--;
   if (!m_refcount) {
-    if (actionHook::is_linked())
+    if (action_hook.is_linked())
       p_stateSet->erase(p_stateSet->iterator_to(*this));
     if (getVariable())
       lmm_variable_free(getModel()->getMaxminSystem(), getVariable());
     if (getModel()->getUpdateMechanism() == UM_LAZY) {
       /* remove from heap */
       heapRemove(getModel()->getActionHeap());
-      if (actionLmmHook::is_linked())
+      if (action_lmm_hook.is_linked())
         getModel()->getModifiedSet()->erase(getModel()->getModifiedSet()->iterator_to(*this));
     }
     delete this;
index b9f27ee..61bfdca 100644 (file)
 #define surf_callback_emit(callback, ...) callback(__VA_ARGS__)
 #endif
 
-extern tmgr_history_t history;
+#ifdef _MSC_VER
+#pragma warning( disable : 4251)
+// 4251: needs to have dll-interface to be used by clients of class
+#endif
+
+extern XBT_PRIVATE tmgr_history_t history;
 #define NO_MAX_DURATION -1.0
 
 using namespace std;
@@ -43,36 +48,27 @@ using namespace std;
  *********/
 
 /* user-visible parameters */
-extern double sg_tcp_gamma;
-extern double sg_sender_gap;
-extern double sg_latency_factor;
-extern double sg_bandwidth_factor;
-extern double sg_weight_S_parameter;
-extern int sg_network_crosstraffic;
-extern xbt_dynar_t surf_path;
+extern XBT_PRIVATE double sg_tcp_gamma;
+extern XBT_PRIVATE double sg_sender_gap;
+extern XBT_PRIVATE double sg_latency_factor;
+extern XBT_PRIVATE double sg_bandwidth_factor;
+extern XBT_PRIVATE double sg_weight_S_parameter;
+extern XBT_PRIVATE int sg_network_crosstraffic;
+extern XBT_PRIVATE xbt_dynar_t surf_path;
 
 extern "C" {
 XBT_PUBLIC(double) surf_get_clock(void);
 }
 
-extern double sg_sender_gap;
+extern XBT_PRIVATE double sg_sender_gap;
 
-extern surf_callback(void, void) surfExitCallbacks;
+extern XBT_PRIVATE surf_callback(void, void) surfExitCallbacks;
 
-int __surf_is_absolute_file_path(const char *file_path);
+int XBT_PRIVATE __surf_is_absolute_file_path(const char *file_path);
 
 /***********
  * Classes *
  ***********/
-typedef boost::intrusive::list<Action> ActionList;
-typedef ActionList* ActionListPtr;
-typedef boost::intrusive::list_base_hook<> actionHook;
-
-struct lmmTag;
-typedef boost::intrusive::list<Action, boost::intrusive::base_hook<boost::intrusive::list_base_hook<boost::intrusive::tag<lmmTag> > > > ActionLmmList;
-typedef ActionLmmList* ActionLmmListPtr;
-typedef boost::intrusive::list_base_hook<boost::intrusive::tag<lmmTag> > actionLmmHook;
-
 
 enum heap_action_type{
   LATENCY = 100,
@@ -92,6 +88,188 @@ XBT_PUBLIC_DATA(xbt_dict_t) trace_connect_list_link_avail;
 XBT_PUBLIC_DATA(xbt_dict_t) trace_connect_list_bandwidth;
 XBT_PUBLIC_DATA(xbt_dict_t) trace_connect_list_latency;
 
+/**********
+ * Action *
+ **********/
+XBT_PRIVATE void surf_action_lmm_update_index_heap(void *action, int i);
+
+/** @ingroup SURF_interface
+ * @brief SURF action interface class
+ * @details An action is an event generated by a resource (e.g.: a communication for the network)
+ */
+XBT_PUBLIC_CLASS Action {
+public:
+  boost::intrusive::list_member_hook<> action_hook;
+  boost::intrusive::list_member_hook<> action_lmm_hook;
+  typedef boost::intrusive::member_hook<
+    Action, boost::intrusive::list_member_hook<>, &Action::action_hook> ActionOptions;
+  typedef boost::intrusive::list<Action, ActionOptions> ActionList;
+private:
+  /**
+   * @brief Common initializations for the constructors
+   */
+  void initialize(Model *model, double cost, bool failed,
+                  lmm_variable_t var = NULL);
+
+public:
+  /**
+   * @brief Action constructor
+   *
+   * @param model The Model associated to this Action
+   * @param cost The cost of the Action
+   * @param failed If the action is impossible (e.g.: execute something on a switched off host)
+   */
+  Action(Model *model, double cost, bool failed);
+
+  /**
+   * @brief Action constructor
+   *
+   * @param model The Model associated to this Action
+   * @param cost The cost of the Action
+   * @param failed If the action is impossible (e.g.: execute something on a switched off host)
+   * @param var The lmm variable associated to this Action if it is part of a LMM component
+   */
+  Action(Model *model, double cost, bool failed, lmm_variable_t var);
+
+  /** @brief Destructor */
+  virtual ~Action();
+
+  /** @brief Mark that the action is now finished */
+  void finish();
+
+  /** @brief Get the [state](\ref e_surf_action_state_t) of the current Action */
+  e_surf_action_state_t getState(); /**< get the state*/
+  /** @brief Set the [state](\ref e_surf_action_state_t) of the current Action */
+  virtual void setState(e_surf_action_state_t state);
+
+  /** @brief Get the bound of the current Action */
+  double getBound();
+  /** @brief Set the bound of the current Action */
+  void setBound(double bound);
+
+  /** @brief Get the start time of the current action */
+  double getStartTime();
+  /** @brief Get the finish time of the current action */
+  double getFinishTime();
+
+  /** @brief Get the user data associated to the current action */
+  void *getData() {return p_data;}
+  /** @brief Set the user data associated to the current action */
+  void setData(void* data);
+
+  /** @brief Get the cost of the current action */
+  double getCost() {return m_cost;}
+  /** @brief Set the cost of the current action */
+  void setCost(double cost) {m_cost = cost;}
+
+  /** @brief Update the maximum duration of the current action
+   *  @param delta Amount to remove from the MaxDuration */
+  void updateMaxDuration(double delta) {double_update(&m_maxDuration, delta,sg_surf_precision);}
+
+  /** @brief Update the remaining time of the current action
+   *  @param delta Amount to remove from the remaining time */
+  void updateRemains(double delta) {double_update(&m_remains, delta, sg_maxmin_precision*sg_surf_precision);}
+
+  /** @brief Set the remaining time of the current action */
+  void setRemains(double value) {m_remains = value;}
+  /** @brief Get the remaining time of the current action after updating the resource */
+  virtual double getRemains();
+  /** @brief Get the remaining time of the current action without updating the resource */
+  double getRemainsNoUpdate();
+
+  /** @brief Set the finish time of the current action */
+  void setFinishTime(double value) {m_finish = value;}
+
+  /**@brief Add a reference to the current action (refcounting) */
+  void ref();
+  /** @brief Unref that action (and destroy it if refcount reaches 0)
+   *  @return true if the action was destroyed and false if someone still has references on it
+   */
+  virtual int unref();
+
+  /** @brief Cancel the current Action if running */
+  virtual void cancel();
+
+  /** @brief Suspend the current Action */
+  virtual void suspend();
+
+  /** @brief Resume the current Action */
+  virtual void resume();
+
+  /** @brief Returns true if the current action is running */
+  virtual bool isSuspended();
+
+  /** @brief Get the maximum duration of the current action */
+  double getMaxDuration() {return m_maxDuration;}
+  /** @brief Set the maximum duration of the current Action */
+  virtual void setMaxDuration(double duration);
+
+  /** @brief Get the tracing category associated to the current action */
+  char *getCategory() {return p_category;}
+  /** @brief Set the tracing category of the current Action */
+  void setCategory(const char *category);
+
+  /** @brief Get the priority of the current Action */
+  double getPriority() {return m_priority;};
+  /** @brief Set the priority of the current Action */
+  virtual void setPriority(double priority);
+
+  /** @brief Get the state set in which the action is */
+  ActionList* getStateSet() {return p_stateSet;};
+
+  s_xbt_swag_hookup_t p_stateHookup;
+
+  Model *getModel() {return p_model;}
+
+protected:
+  ActionList* p_stateSet;
+  double m_priority; /**< priority (1.0 by default) */
+  int    m_refcount;
+  double m_remains; /**< How much of that cost remains to be done in the currently running task */
+  double m_maxDuration; /*< max_duration (may fluctuate until the task is completed) */
+  double m_finish; /**< finish time : this is modified during the run and fluctuates until the task is completed */
+
+private:
+  double m_start; /**< start time  */
+  char *p_category;               /**< tracing category for categorized resource utilization monitoring */
+
+  #ifdef HAVE_LATENCY_BOUND_TRACKING
+  int m_latencyLimited;               /**< Set to 1 if is limited by latency, 0 otherwise */
+  #endif
+  double    m_cost;
+  Model *p_model;
+  void *p_data; /**< for your convenience */
+
+  /* LMM */
+public:
+  virtual void updateRemainingLazy(double now);
+  void heapInsert(xbt_heap_t heap, double key, enum heap_action_type hat);
+  void heapRemove(xbt_heap_t heap);
+  void heapUpdate(xbt_heap_t heap, double key, enum heap_action_type hat);
+  void updateIndexHeap(int i);
+  lmm_variable_t getVariable() {return p_variable;}
+  double getLastUpdate() {return m_lastUpdate;}
+  void refreshLastUpdate() {m_lastUpdate = surf_get_clock();}
+  enum heap_action_type getHat() {return m_hat;}
+  bool is_linked() {return action_lmm_hook.is_linked();}
+  void gapRemove();
+
+protected:
+  lmm_variable_t p_variable;
+  double m_lastValue;
+  double m_lastUpdate;
+  int m_suspended;
+  int m_indexHeap;
+  enum heap_action_type m_hat;
+};
+
+typedef Action::ActionList ActionList;
+
+typedef boost::intrusive::member_hook<
+  Action, boost::intrusive::list_member_hook<>, &Action::action_lmm_hook> ActionLmmOptions;
+typedef boost::intrusive::list<Action, ActionLmmOptions> ActionLmmList;
+typedef ActionLmmList* ActionLmmListPtr;
+
 /*********
  * Model *
  *********/
@@ -115,28 +293,28 @@ public:
    *
    * @return The set of [actions](@ref Action) in *ready* state
    */
-  virtual ActionListPtr getReadyActionSet() {return p_readyActionSet;}
+  virtual ActionList* getReadyActionSet() {return p_readyActionSet;}
 
   /**
    * @brief Get the set of [actions](@ref Action) in *running* state
    *
    * @return The set of [actions](@ref Action) in *running* state
    */
-  virtual ActionListPtr getRunningActionSet() {return p_runningActionSet;}
+  virtual ActionList* getRunningActionSet() {return p_runningActionSet;}
 
   /**
    * @brief Get the set of [actions](@ref Action) in *failed* state
    *
    * @return The set of [actions](@ref Action) in *failed* state
    */
-  virtual ActionListPtr getFailedActionSet() {return p_failedActionSet;}
+  virtual ActionList* getFailedActionSet() {return p_failedActionSet;}
 
   /**
    * @brief Get the set of [actions](@ref Action) in *done* state
    *
    * @return The set of [actions](@ref Action) in *done* state
    */
-  virtual ActionListPtr getDoneActionSet() {return p_doneActionSet;}
+  virtual ActionList* getDoneActionSet() {return p_doneActionSet;}
 
   /**
    * @brief Get the set of modified [actions](@ref Action)
@@ -178,7 +356,7 @@ public:
   virtual double shareResources(double now);
   virtual double shareResourcesLazy(double now);
   virtual double shareResourcesFull(double now);
-  double shareResourcesMaxMin(ActionListPtr running_actions,
+  double shareResourcesMaxMin(ActionList* running_actions,
                                       lmm_system_t sys,
                                       void (*solve) (lmm_system_t));
 
@@ -208,10 +386,10 @@ protected:
   xbt_heap_t p_actionHeap;
 
 private:
-  ActionListPtr p_readyActionSet; /**< Actions in state SURF_ACTION_READY */
-  ActionListPtr p_runningActionSet; /**< Actions in state SURF_ACTION_RUNNING */
-  ActionListPtr p_failedActionSet; /**< Actions in state SURF_ACTION_FAILED */
-  ActionListPtr p_doneActionSet; /**< Actions in state SURF_ACTION_DONE */
+  ActionList* p_readyActionSet; /**< Actions in state SURF_ACTION_READY */
+  ActionList* p_runningActionSet; /**< Actions in state SURF_ACTION_RUNNING */
+  ActionList* p_failedActionSet; /**< Actions in state SURF_ACTION_FAILED */
+  ActionList* p_doneActionSet; /**< Actions in state SURF_ACTION_DONE */
 };
 
 /************
@@ -358,173 +536,4 @@ private:
   lmm_constraint_t p_constraint;
 };
 
-/**********
- * Action *
- **********/
-void surf_action_lmm_update_index_heap(void *action, int i);
-
-/** @ingroup SURF_interface
- * @brief SURF action interface class
- * @details An action is an event generated by a resource (e.g.: a communication for the network)
- */
-XBT_PUBLIC_CLASS Action : public actionHook, public actionLmmHook {
-private:
-  /**
-   * @brief Common initializations for the constructors
-   */
-  void initialize(Model *model, double cost, bool failed,
-                  lmm_variable_t var = NULL);
-
-public:
-  /**
-   * @brief Action constructor
-   *
-   * @param model The Model associated to this Action
-   * @param cost The cost of the Action
-   * @param failed If the action is impossible (e.g.: execute something on a switched off host)
-   */
-  Action(Model *model, double cost, bool failed);
-
-  /**
-   * @brief Action constructor
-   *
-   * @param model The Model associated to this Action
-   * @param cost The cost of the Action
-   * @param failed If the action is impossible (e.g.: execute something on a switched off host)
-   * @param var The lmm variable associated to this Action if it is part of a LMM component
-   */
-  Action(Model *model, double cost, bool failed, lmm_variable_t var);
-
-  /** @brief Destructor */
-  virtual ~Action();
-
-  /** @brief Mark that the action is now finished */
-  void finish();
-
-  /** @brief Get the [state](\ref e_surf_action_state_t) of the current Action */
-  e_surf_action_state_t getState(); /**< get the state*/
-  /** @brief Set the [state](\ref e_surf_action_state_t) of the current Action */
-  virtual void setState(e_surf_action_state_t state);
-
-  /** @brief Get the bound of the current Action */
-  double getBound();
-  /** @brief Set the bound of the current Action */
-  void setBound(double bound);
-
-  /** @brief Get the start time of the current action */
-  double getStartTime();
-  /** @brief Get the finish time of the current action */
-  double getFinishTime();
-
-  /** @brief Get the user data associated to the current action */
-  void *getData() {return p_data;}
-  /** @brief Set the user data associated to the current action */
-  void setData(void* data);
-
-  /** @brief Get the cost of the current action */
-  double getCost() {return m_cost;}
-  /** @brief Set the cost of the current action */
-  void setCost(double cost) {m_cost = cost;}
-
-  /** @brief Update the maximum duration of the current action
-   *  @param delta Amount to remove from the MaxDuration */
-  void updateMaxDuration(double delta) {double_update(&m_maxDuration, delta,sg_surf_precision);}
-
-  /** @brief Update the remaining time of the current action
-   *  @param delta Amount to remove from the remaining time */
-  void updateRemains(double delta) {double_update(&m_remains, delta, sg_maxmin_precision*sg_surf_precision);}
-
-  /** @brief Set the remaining time of the current action */
-  void setRemains(double value) {m_remains = value;}
-  /** @brief Get the remaining time of the current action after updating the resource */
-  virtual double getRemains();
-  /** @brief Get the remaining time of the current action without updating the resource */
-  double getRemainsNoUpdate();
-
-  /** @brief Set the finish time of the current action */
-  void setFinishTime(double value) {m_finish = value;}
-
-  /**@brief Add a reference to the current action (refcounting) */
-  void ref();
-  /** @brief Unref that action (and destroy it if refcount reaches 0)
-   *  @return true if the action was destroyed and false if someone still has references on it
-   */
-  virtual int unref();
-
-  /** @brief Cancel the current Action if running */
-  virtual void cancel();
-
-  /** @brief Suspend the current Action */
-  virtual void suspend();
-
-  /** @brief Resume the current Action */
-  virtual void resume();
-
-  /** @brief Returns true if the current action is running */
-  virtual bool isSuspended();
-
-  /** @brief Get the maximum duration of the current action */
-  double getMaxDuration() {return m_maxDuration;}
-  /** @brief Set the maximum duration of the current Action */
-  virtual void setMaxDuration(double duration);
-
-  /** @brief Get the tracing category associated to the current action */
-  char *getCategory() {return p_category;}
-  /** @brief Set the tracing category of the current Action */
-  void setCategory(const char *category);
-
-  /** @brief Get the priority of the current Action */
-  double getPriority() {return m_priority;};
-  /** @brief Set the priority of the current Action */
-  virtual void setPriority(double priority);
-
-  /** @brief Get the state set in which the action is */
-  ActionListPtr getStateSet() {return p_stateSet;};
-
-  s_xbt_swag_hookup_t p_stateHookup;
-
-  Model *getModel() {return p_model;}
-
-protected:
-  ActionListPtr p_stateSet;
-  double m_priority; /**< priority (1.0 by default) */
-  int    m_refcount;
-  double m_remains; /**< How much of that cost remains to be done in the currently running task */
-  double m_maxDuration; /*< max_duration (may fluctuate until the task is completed) */
-  double m_finish; /**< finish time : this is modified during the run and fluctuates until the task is completed */
-
-private:
-  double m_start; /**< start time  */
-  char *p_category;               /**< tracing category for categorized resource utilization monitoring */
-
-  #ifdef HAVE_LATENCY_BOUND_TRACKING
-  int m_latencyLimited;               /**< Set to 1 if is limited by latency, 0 otherwise */
-  #endif
-  double    m_cost;
-  Model *p_model;
-  void *p_data; /**< for your convenience */
-
-  /* LMM */
-public:
-  virtual void updateRemainingLazy(double now);
-  void heapInsert(xbt_heap_t heap, double key, enum heap_action_type hat);
-  void heapRemove(xbt_heap_t heap);
-  void heapUpdate(xbt_heap_t heap, double key, enum heap_action_type hat);
-  void updateIndexHeap(int i);
-  lmm_variable_t getVariable() {return p_variable;}
-  double getLastUpdate() {return m_lastUpdate;}
-  void refreshLastUpdate() {m_lastUpdate = surf_get_clock();}
-  enum heap_action_type getHat() {return m_hat;}
-  bool is_linked() {return actionLmmHook::is_linked();}
-  void gapRemove();
-
-protected:
-  lmm_variable_t p_variable;
-  double m_lastValue;
-  double m_lastUpdate;
-  int m_suspended;
-  int m_indexHeap;
-  enum heap_action_type m_hat;
-};
-
 #endif /* SURF_MODEL_H_ */
index e69d8f4..da772b5 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef _SURF_SURF_PRIVATE_H
 #define _SURF_SURF_PRIVATE_H
 
+#include <xbt/base.h>
+
 #include "surf/surf.h"
 #include "surf/maxmin.h"
 #include "surf/trace_mgr.h"
@@ -22,7 +24,7 @@ SG_BEGIN_DECL()
 
 XBT_PUBLIC_DATA(xbt_dict_t) watched_hosts_lib;
 
-extern const char *surf_action_state_names[6];
+extern XBT_PRIVATE const char *surf_action_state_names[6];
 
 /** @ingroup SURF_interface
  * @brief Possible update mechanisms
@@ -35,15 +37,15 @@ typedef enum {
 
 /* Generic functions common to all models */
 
-FILE *surf_fopen(const char *name, const char *mode);
+XBT_PRIVATE FILE *surf_fopen(const char *name, const char *mode);
 
-extern tmgr_history_t history;
+extern XBT_PRIVATE tmgr_history_t history;
 
 /* The __surf_is_absolute_file_path() returns 1 if
  * file_path is a absolute file path, in the other
  * case the function returns 0.
  */
-int __surf_is_absolute_file_path(const char *file_path);
+XBT_PRIVATE int __surf_is_absolute_file_path(const char *file_path);
 
 /**
  * Routing logic
index 1d29998..fbe19f2 100644 (file)
@@ -4,28 +4,45 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include "surf_interface.hpp"
-#include <float.h>
-
 #ifndef NETWORK_ROUTING_HPP_
 #define NETWORK_ROUTING_HPP_
 
+#include <xbt/base.h>
+
+#include "surf_interface.hpp"
+#include <float.h>
+
 XBT_PUBLIC(void) routing_model_create( void *loopback);
 
 /* ************************************************************************** */
 /* ************************* GRAPH EXPORTING FUNCTIONS ********************** */
-xbt_node_t new_xbt_graph_node (xbt_graph_t graph, const char *name, xbt_dict_t nodes);
-xbt_edge_t new_xbt_graph_edge (xbt_graph_t graph, xbt_node_t s, xbt_node_t d, xbt_dict_t edges);
+XBT_PRIVATE xbt_node_t new_xbt_graph_node (xbt_graph_t graph, const char *name, xbt_dict_t nodes);
+XBT_PRIVATE xbt_edge_t new_xbt_graph_edge (xbt_graph_t graph, xbt_node_t s, xbt_node_t d, xbt_dict_t edges);
 
 /***********
  * Classes *
  ***********/
 
 class As;
-class RoutingModelDescription;
-class Onelink;
+class XBT_PRIVATE RoutingModelDescription;
+class XBT_PRIVATE Onelink;
 class RoutingPlatf;
 
+/** @ingroup SURF_routing_interface
+ * @brief A routing edge
+ * @details [long description]
+ */
+struct RoutingEdge {
+public:
+  virtual ~RoutingEdge(){};
+  virtual int getId()=0;
+  virtual int *getIdPtr()=0;
+  virtual void setId(int id)=0;
+  virtual char *getName()=0;
+  virtual As *getRcComponent()=0;
+  virtual e_surf_network_element_type_t getRcType()=0;
+};
+
 /** @ingroup SURF_routing_interface
  * @brief The Autonomous System (AS) routing interface
  * @details [TODO]
@@ -52,6 +69,8 @@ public:
    */
   virtual ~As(){
        xbt_free(p_name);
+       if (p_netElem)
+               delete p_netElem;
   };
 
   /**
@@ -79,22 +98,7 @@ public:
   virtual void parseBypassroute(sg_platf_route_cbarg_t e_route)=0;
 };
 
-/** @ingroup SURF_routing_interface
- * @brief A routing edge
- * @details [long description]
- */
-struct RoutingEdge {
-public:
-  virtual ~RoutingEdge(){};
-  virtual int getId()=0;
-  virtual int *getIdPtr()=0;
-  virtual void setId(int id)=0;
-  virtual char *getName()=0;
-  virtual As *getRcComponent()=0;
-  virtual e_surf_network_element_type_t getRcType()=0;
-};
-
-struct RoutingEdgeImpl : public RoutingEdge {
+struct XBT_PRIVATE RoutingEdgeImpl : public RoutingEdge {
 public:
   RoutingEdgeImpl(char *name, int id, e_surf_network_element_type_t rcType, As *rcComponent)
   : p_rcComponent(rcComponent), p_rcType(rcType), m_id(id), p_name(name) {}
index e0f85d6..c7fa8c8 100644 (file)
@@ -7,13 +7,15 @@
 #ifndef SURF_ROUTING_CLUSTER_HPP_
 #define SURF_ROUTING_CLUSTER_HPP_
 
+#include <xbt/base.h>
+
 #include "surf_routing_none.hpp"
 #include "network_interface.hpp"
 
 /***********
  * Classes *
  ***********/
-class AsCluster;
+class XBT_PRIVATE AsCluster;
 
 
 /* ************************************************** */
index 2180d06..91a2c46 100644 (file)
@@ -7,6 +7,8 @@
 #ifndef SURF_ROUTING_CLUSTER_FAT_TREE_HPP_
 #define SURF_ROUTING_CLUSTER_FAT_TREE_HPP_
 
+#include <xbt/base.h>
+
 #include "surf_routing_cluster.hpp"
 
 
@@ -17,8 +19,8 @@
  * address real world constraints, which are not currently enforced. 
  */
 
-class FatTreeNode;
-class FatTreeLink;
+class XBT_PRIVATE FatTreeNode;
+class XBT_PRIVATE FatTreeLink;
 
 /** \brief A node in a fat tree.
  * A FatTreeNode can either be a switch or a processing node. Switches are
@@ -107,7 +109,7 @@ public:
  *
  * Routing is made using a destination-mod-k scheme.
  */
-class AsClusterFatTree : public AsCluster {
+class XBT_PRIVATE AsClusterFatTree : public AsCluster {
 public:
   AsClusterFatTree();
   ~AsClusterFatTree();
index bd1f9e7..0408989 100644 (file)
@@ -8,11 +8,13 @@
 #ifndef SURF_ROUTING_CLUSTER_TORUS_HPP_
 #define SURF_ROUTING_CLUSTER_TORUS_HPP_
 
+#include <xbt/base.h>
+
 #include "surf_routing_none.hpp"
 #include "network_interface.hpp"
 #include "surf_routing_cluster.hpp"
 
-class AsClusterTorus: public AsCluster {
+class XBT_PRIVATE AsClusterTorus: public AsCluster {
 public:
    AsClusterTorus();
    virtual ~AsClusterTorus();
index ee2c80c..aa84000 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "surf_routing_generic.hpp"
 
 #ifndef SURF_ROUTING_DIJKSTRA_HPP_
@@ -26,7 +28,7 @@ typedef struct route_cache_element {
 /***********
  * Classes *
  ***********/
-class AsDijkstra;
+class XBT_PRIVATE AsDijkstra;
 
 class AsDijkstra : public AsGeneric {
 public:
index ed39b19..592e0d5 100644 (file)
@@ -8,12 +8,14 @@
 #ifndef SURF_ROUTING_FLOYD_HPP_
 #define SURF_ROUTING_FLOYD_HPP_
 
+#include <xbt/base.h>
+
 #include "surf_routing_generic.hpp"
 
 /***********
  * Classes *
  ***********/
-class AsFloyd;
+class XBT_PRIVATE AsFloyd;
 
 class AsFloyd: public AsGeneric {
 public:
index e4bc28d..1a0a011 100644 (file)
@@ -7,12 +7,14 @@
 #ifndef SURF_ROUTING_FULL_HPP_
 #define SURF_ROUTING_FULL_HPP_
 
+#include <xbt/base.h>
+
 #include "surf_routing_generic.hpp"
 
 /***********
  * Classes *
  ***********/
-class AsFull;
+class XBT_PRIVATE AsFull;
 
 class AsFull: public AsGeneric {
 public:
index 7eed697..d397ae1 100644 (file)
@@ -4,16 +4,18 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "surf_routing_none.hpp"
 
 #ifndef SURF_ROUTING_GENERIC_HPP_
 #define SURF_ROUTING_GENERIC_HPP_
 
-class AsGeneric;
+class XBT_PRIVATE AsGeneric;
 
 void generic_free_route(sg_platf_route_cbarg_t route);
 
-class AsGeneric : public AsNone {
+class XBT_PRIVATE AsGeneric : public AsNone {
 public:
   AsGeneric();
   ~AsGeneric();
index 4995469..4652b56 100644 (file)
@@ -17,7 +17,7 @@ xbt_dynar_t AsNone::getOneLinkRoutes() {
   return NULL;
 }
 
-void AsNone::getRouteAndLatency(RoutingEdge */*src*/, RoutingEdge */*dst*/,
+void AsNone::getRouteAndLatency(RoutingEdge * /*src*/, RoutingEdge * /*dst*/,
                                 sg_platf_route_cbarg_t /*res*/, double *lat)
 {
   *lat = 0.0;
@@ -28,7 +28,7 @@ void AsNone::getGraph(xbt_graph_t /*graph*/, xbt_dict_t /*nodes*/, xbt_dict_t /*
        XBT_INFO("No routing no graph");
 }
 
-sg_platf_route_cbarg_t AsNone::getBypassRoute(RoutingEdge */*src*/, RoutingEdge */*dst*/, double */*lat*/) {
+sg_platf_route_cbarg_t AsNone::getBypassRoute(RoutingEdge * /*src*/, RoutingEdge * /*dst*/, double * /*lat*/) {
   return NULL;
 }
 
index 3063261..e69fade 100644 (file)
@@ -4,12 +4,14 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "surf_routing.hpp"
 
 #ifndef SURF_ROUTING_NONE_HPP_
 #define SURF_ROUTING_NONE_HPP_
 
-class AsNone : public As {
+class XBT_PRIVATE AsNone : public As {
 public:
   AsNone();
   ~AsNone();
index a51a7de..4892818 100644 (file)
@@ -11,6 +11,7 @@
 #include "internal_config.h"
 
 #include "surf_interface.hpp"
+#include "xbt/base.h"
 #include "xbt/dynar.h"
 #include "xbt/str.h"
 #include "xbt/config.h"
 /* ************************************************************************** */
 /* ******************************* NO ROUTING ******************************* */
 /* Only save the AS tree, and forward calls to child ASes */
-AS_t model_none_create(void);
-AS_t model_none_create_sized(size_t childsize);
-void model_none_finalize(AS_t as);
+XBT_PRIVATE AS_t model_none_create(void);
+XBT_PRIVATE AS_t model_none_create_sized(size_t childsize);
+XBT_PRIVATE void model_none_finalize(AS_t as);
 /* ************************************************************************** */
 /* ***************** GENERIC PARSE FUNCTIONS (declarations) ***************** */
-AS_t model_generic_create_sized(size_t childsize);
-void model_generic_finalize(AS_t as);
+XBT_PRIVATE AS_t model_generic_create_sized(size_t childsize);
+XBT_PRIVATE void model_generic_finalize(AS_t as);
 
-int generic_parse_PU(AS_t rc, sg_routing_edge_t elm);
-int generic_parse_AS(AS_t rc, sg_routing_edge_t elm);
-void generic_parse_bypassroute(AS_t rc, sg_platf_route_cbarg_t e_route);
+XBT_PRIVATE int generic_parse_PU(AS_t rc, sg_routing_edge_t elm);
+XBT_PRIVATE int generic_parse_AS(AS_t rc, sg_routing_edge_t elm);
+XBT_PRIVATE void generic_parse_bypassroute(AS_t rc, sg_platf_route_cbarg_t e_route);
 
 /* ************************************************************************** */
 /* *************** GENERIC BUSINESS METHODS (declarations) ****************** */
 
-xbt_dynar_t generic_get_onelink_routes(AS_t rc);
-sg_platf_route_cbarg_t generic_get_bypassroute(AS_t rc,
+XBT_PRIVATE xbt_dynar_t generic_get_onelink_routes(AS_t rc);
+XBT_PRIVATE sg_platf_route_cbarg_t generic_get_bypassroute(AS_t rc,
     sg_routing_edge_t src,
     sg_routing_edge_t dst,
     double *lat);
@@ -48,53 +49,53 @@ sg_platf_route_cbarg_t generic_get_bypassroute(AS_t rc,
 /* change a route containing link names into a route containing link entities.
  * If change_order is true, the links are put in reverse order in the
  * produced route */
-sg_platf_route_cbarg_t generic_new_extended_route(e_surf_routing_hierarchy_t hierarchy,
+XBT_PRIVATE sg_platf_route_cbarg_t generic_new_extended_route(e_surf_routing_hierarchy_t hierarchy,
                                    sg_platf_route_cbarg_t data, int preserve_order);
-AS_t
+XBT_PRIVATE AS_t
 generic_autonomous_system_exist(AS_t rc, char *element);
-AS_t
+XBT_PRIVATE AS_t
 generic_processing_units_exist(AS_t rc, char *element);
 void generic_src_dst_check(AS_t rc, sg_routing_edge_t src,
     sg_routing_edge_t dst);
 
 /* ************************************************************************** */
 /* *************************** FLOYD ROUTING ******************************** */
-AS_t model_floyd_create(void);  /* create structures for floyd routing model */
-void model_floyd_end(AS_t as);      /* finalize the creation of floyd routing model */
-void model_floyd_parse_route(AS_t rc, sg_platf_route_cbarg_t route);
+XBT_PRIVATE AS_t model_floyd_create(void);  /* create structures for floyd routing model */
+XBT_PRIVATE void model_floyd_end(AS_t as);      /* finalize the creation of floyd routing model */
+XBT_PRIVATE void model_floyd_parse_route(AS_t rc, sg_platf_route_cbarg_t route);
 
 /* ************************************************** */
 /* **************  Cluster ROUTING   **************** */
 
-As *model_cluster_create(void);      /* create structures for cluster routing model */
-As *model_torus_cluster_create(void);
-As *model_fat_tree_cluster_create(void);
+XBT_PRIVATE As *model_cluster_create(void);      /* create structures for cluster routing model */
+XBT_PRIVATE As *model_torus_cluster_create(void);
+XBT_PRIVATE As *model_fat_tree_cluster_create(void);
 
 /* ************************************************** */
 /* **************  Vivaldi ROUTING   **************** */
-AS_t model_vivaldi_create(void);      /* create structures for vivaldi routing model */
+XBT_PRIVATE AS_t model_vivaldi_create(void);      /* create structures for vivaldi routing model */
 #define HOST_PEER(peername) bprintf("peer_%s", peername)
 #define ROUTER_PEER(peername) bprintf("router_%s", peername)
 #define LINK_PEER(peername) bprintf("link_%s", peername)
 
 /* ************************************************************************** */
 /* ********** Dijkstra & Dijkstra Cached ROUTING **************************** */
-AS_t model_dijkstra_both_create(int cached);    /* create by calling dijkstra or dijkstracache */
-AS_t model_dijkstra_create(void);       /* create structures for dijkstra routing model */
-AS_t model_dijkstracache_create(void);  /* create structures for dijkstracache routing model */
-void model_dijkstra_both_end(AS_t as);      /* finalize the creation of dijkstra routing model */
-void model_dijkstra_both_parse_route (AS_t rc, sg_platf_route_cbarg_t route);
+XBT_PRIVATE AS_t model_dijkstra_both_create(int cached);    /* create by calling dijkstra or dijkstracache */
+XBT_PRIVATE AS_t model_dijkstra_create(void);       /* create structures for dijkstra routing model */
+XBT_PRIVATE AS_t model_dijkstracache_create(void);  /* create structures for dijkstracache routing model */
+XBT_PRIVATE void model_dijkstra_both_end(AS_t as);      /* finalize the creation of dijkstra routing model */
+XBT_PRIVATE void model_dijkstra_both_parse_route (AS_t rc, sg_platf_route_cbarg_t route);
 
 /* ************************************************************************** */
 /* *************************** FULL ROUTING ********************************* */
-AS_t model_full_create(void);   /* create structures for full routing model */
-void model_full_end(AS_t as);       /* finalize the creation of full routing model */
-void model_full_set_route(  /* Set the route and ASroute between src and dst */
+XBT_PRIVATE AS_t model_full_create(void);   /* create structures for full routing model */
+XBT_PRIVATE void model_full_end(AS_t as);       /* finalize the creation of full routing model */
+XBT_PRIVATE void model_full_set_route(  /* Set the route and ASroute between src and dst */
     AS_t rc, sg_platf_route_cbarg_t route);
 /* ************************************************************************** */
 /* ************************* GRAPH EXPORTING FUNCTIONS ********************** */
-xbt_node_t new_xbt_graph_node (xbt_graph_t graph, const char *name, xbt_dict_t nodes);
-xbt_edge_t new_xbt_graph_edge (xbt_graph_t graph, xbt_node_t s, xbt_node_t d, xbt_dict_t edges);
+XBT_PRIVATE xbt_node_t new_xbt_graph_node (xbt_graph_t graph, const char *name, xbt_dict_t nodes);
+XBT_PRIVATE xbt_edge_t new_xbt_graph_edge (xbt_graph_t graph, xbt_node_t s, xbt_node_t d, xbt_dict_t edges);
 
 
 #endif                          /* _SURF_SURF_ROUTING_PRIVATE_H */
index 8dd4df6..6d1094c 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include "xbt/swag.h"
+
 #include "surf_routing_generic.hpp"
 
 #ifndef SURF_ROUTING_VIVALDI_HPP_
@@ -11,7 +13,7 @@
 
 /* ************************************************** */
 /* **************  Vivaldi ROUTING   **************** */
-AS_t model_vivaldi_create(void);      /* create structures for vivaldi routing model */
+XBT_PRIVATE AS_t model_vivaldi_create(void);      /* create structures for vivaldi routing model */
 #define HOST_PEER(peername) bprintf("peer_%s", peername)
 #define ROUTER_PEER(peername) bprintf("router_%s", peername)
 #define LINK_PEER(peername) bprintf("link_%s", peername)
@@ -19,7 +21,7 @@ AS_t model_vivaldi_create(void);      /* create structures for vivaldi routing m
 /***********
  * Classes *
  ***********/
-class AsVivaldi;
+class XBT_PRIVATE AsVivaldi;
 
 class AsVivaldi: public AsGeneric {
 public:
index ad461b9..4764cb9 100644 (file)
@@ -7,11 +7,11 @@
 #include <errno.h>
 #include <math.h>
 #include <stdarg.h> /* va_arg */
-#include <libgen.h>
 
 #include "xbt/misc.h"
 #include "xbt/log.h"
 #include "xbt/str.h"
+#include "xbt/file.h"
 #include "xbt/dict.h"
 #include "surf/surfxml_parse.h"
 #include "surf/surf_private.h"
@@ -374,7 +374,7 @@ void surf_parse_free_callbacks(void)
 /* Stag and Etag parse functions */
 
 void STag_surfxml_platform(void) {
-  _XBT_GNUC_UNUSED double version = surf_parse_get_double(A_surfxml_platform_version);
+  XBT_ATTRIB_UNUSED double version = surf_parse_get_double(A_surfxml_platform_version);
 
   xbt_assert((version >= 1.0), "******* BIG FAT WARNING *********\n "
       "You're using an ancient XML file.\n"
@@ -1028,8 +1028,9 @@ void surf_parse_open(const char *file)
 
   if (!surf_parsed_filename_stack)
     surf_parsed_filename_stack = xbt_dynar_new(sizeof(char *), &xbt_free_ref);
+
   surf_parsed_filename = xbt_strdup(file);
-  char *dir = dirname(surf_parsed_filename);
+  char *dir = xbt_dirname(file);
   xbt_dynar_push(surf_path, &dir);
 
   surf_file_to_parse = surf_fopen(file, "r");
index 820b245..a84a638 100644 (file)
@@ -7,6 +7,7 @@
 #ifndef _SURF_TMGR_PRIVATE_H
 #define _SURF_TMGR_PRIVATE_H
 
+#include "xbt/base.h"
 #include "xbt/swag.h"
 #include "xbt/heap.h"
 #include "surf/trace_mgr.h"
@@ -70,6 +71,6 @@ typedef struct tmgr_history {
   xbt_heap_t heap;
 } s_tmgr_history_t;
 
-double tmgr_event_generator_next_value(probabilist_event_generator_t generator);
+XBT_PRIVATE double tmgr_event_generator_next_value(probabilist_event_generator_t generator);
 
 #endif                          /* _SURF_TMGR_PRIVATE_H */
index 8936dae..acb25b8 100644 (file)
@@ -62,10 +62,10 @@ double VMHL13Model::shareResources(double now)
   /* 0. Make sure that we already calculated the resource share at the physical
    * machine layer. */
   {
-    _XBT_GNUC_UNUSED Model *ws_model = surf_host_model;
-    _XBT_GNUC_UNUSED Model *vm_ws_model = surf_vm_model;
-    _XBT_GNUC_UNUSED unsigned int index_of_pm_ws_model = xbt_dynar_search(model_list_invoke, &ws_model);
-    _XBT_GNUC_UNUSED unsigned int index_of_vm_ws_model = xbt_dynar_search(model_list_invoke, &vm_ws_model);
+    XBT_ATTRIB_UNUSED Model *ws_model = surf_host_model;
+    XBT_ATTRIB_UNUSED Model *vm_ws_model = surf_vm_model;
+    XBT_ATTRIB_UNUSED unsigned int index_of_pm_ws_model = xbt_dynar_search(model_list_invoke, &ws_model);
+    XBT_ATTRIB_UNUSED unsigned int index_of_vm_ws_model = xbt_dynar_search(model_list_invoke, &vm_ws_model);
     xbt_assert((index_of_pm_ws_model < index_of_vm_ws_model), "Cannot assume surf_host_model comes before");
 
     /* Another option is that we call sub_ws->share_resource() here. The
@@ -260,7 +260,7 @@ VMHL13::VMHL13(VMModel *model, const char* name, xbt_dict_t props,
 VMHL13::~VMHL13()
 {
   /* Free the cpu_action of the VM. */
-  _XBT_GNUC_UNUSED int ret = p_action->unref();
+  XBT_ATTRIB_UNUSED int ret = p_action->unref();
   xbt_assert(ret == 1, "Bug: some resource still remains");
 }
 
@@ -369,7 +369,7 @@ void VMHL13::migrate(surf_resource_t ind_dst_pm)
        new_cpu_action->setBound(old_bound);
      }
 
-     _XBT_GNUC_UNUSED int ret = p_action->unref();
+     XBT_ATTRIB_UNUSED int ret = p_action->unref();
      xbt_assert(ret == 1, "Bug: some resource still remains");
 
      p_action = new_cpu_action;
index 419a826..311c0f8 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include "xbt/base.h"
+
 #include "host_clm03.hpp"
 #include "vm_interface.hpp"
 
@@ -17,8 +19,8 @@
  * Classes *
  ***********/
 
-class VMHL13Model;
-class VMHL13;
+class XBT_PRIVATE VMHL13Model;
+class XBT_PRIVATE VMHL13;
 
 /*********
  * Model *
index 64a4cef..961a04e 100644 (file)
@@ -4,6 +4,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <xbt/base.h>
+
 #include "host_interface.hpp"
 
 #ifndef VM_INTERFACE_HPP_
@@ -16,8 +18,8 @@
  * Classes *
  ***********/
 
-class VMModel;
-class VM;
+class XBT_PRIVATE VMModel;
+class XBT_PRIVATE VM;
 
 /*************
  * Callbacks *
@@ -26,45 +28,17 @@ class VM;
 /** @ingroup SURF_callbacks
  * @brief Callbacks fired after VM creation. Signature: `void(VM*)`
  */
-extern surf_callback(void, VM*) VMCreatedCallbacks;
+extern XBT_PRIVATE surf_callback(void, VM*) VMCreatedCallbacks;
 
 /** @ingroup SURF_callbacks
  * @brief Callbacks fired after VM destruction. Signature: `void(VM*)`
  */
-extern surf_callback(void, VM*) VMDestructedCallbacks;
+extern XBT_PRIVATE surf_callback(void, VM*) VMDestructedCallbacks;
 
 /** @ingroup SURF_callbacks
  * @brief Callbacks after VM State changes. Signature: `void(VMAction*)`
  */
-extern surf_callback(void, VM*) VMStateChangedCallbacks;
-
-/*********
- * Model *
- *********/
-/** @ingroup SURF_vm_interface
- * @brief SURF VM model interface class
- * @details A model is an object which handle the interactions between its Resources and its Actions
- */
-class VMModel : public HostModel {
-public:
-  VMModel() :HostModel(){}
-  ~VMModel(){};
-
-  Host *createHost(const char *name){DIE_IMPOSSIBLE;}
-
-  /**
-   * @brief Create a new VM
-   *
-   * @param name The name of the new VM
-   * @param host_PM The real machine hosting the VM
-   *
-   */
-  virtual VM *createVM(const char *name, surf_resource_t host_PM)=0;
-  void adjustWeightOfDummyCpuActions() {};
-
-  typedef boost::intrusive::list<VM, boost::intrusive::constant_time_size<false> > vm_list_t;
-  static vm_list_t ws_vms;
-};
+extern XBT_PRIVATE surf_callback(void, VM*) VMStateChangedCallbacks;
 
 /************
  * Resource *
@@ -74,8 +48,7 @@ public:
  * @brief SURF VM interface class
  * @details A VM represent a virtual machine
  */
-class VM : public Host,
-           public boost::intrusive::list_base_hook<> {
+class VM : public Host {
 public:
   /**
    * @brief Constructor
@@ -119,6 +92,38 @@ public:
   CpuAction *p_action;
   Host *p_subWs;  // Pointer to the ''host'' OS
   e_surf_vm_state_t p_currentState;
+public:
+  boost::intrusive::list_member_hook<> vm_hook;
+};
+
+/*********
+ * Model *
+ *********/
+/** @ingroup SURF_vm_interface
+ * @brief SURF VM model interface class
+ * @details A model is an object which handle the interactions between its Resources and its Actions
+ */
+class VMModel : public HostModel {
+public:
+  VMModel() :HostModel(){}
+  ~VMModel(){};
+
+  Host *createHost(const char *name){DIE_IMPOSSIBLE;}
+
+  /**
+   * @brief Create a new VM
+   *
+   * @param name The name of the new VM
+   * @param host_PM The real machine hosting the VM
+   *
+   */
+  virtual VM *createVM(const char *name, surf_resource_t host_PM)=0;
+  void adjustWeightOfDummyCpuActions() {};
+
+  typedef boost::intrusive::member_hook<
+    VM, boost::intrusive::list_member_hook<>, &VM::vm_hook> VmOptions;
+  typedef boost::intrusive::list<VM, VmOptions, boost::intrusive::constant_time_size<false> > vm_list_t;
+  static vm_list_t ws_vms;
 };
 
 /**********
diff --git a/src/win32/config.h b/src/win32/config.h
deleted file mode 100644 (file)
index 93ab3bf..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-#ifndef __XBT_WIN32_CONFIG_H__
-#define __XBT_WIN32_CONFIG_H__
-
-
-/* config.h - simgrid config selection for windows platforms. */
-
-/* Copyright (c) 2006-2008, 2010, 2012-2014. The SimGrid Team.
- * All rights reserved.                                                     */
-
-/* This program is free software; you can redistribute it and/or modify it
- * under the terms of the license (GNU LGPL) which comes with this package. */
-
-/* 
- * config selection. 
-*/
-#if defined(__GNUC__)
-        /* data comes from autoconf when using gnuc (cross-compiling?) */
-  # include "internal_config.h"
-  #ifndef _XBT_WIN32
-    typedef unsigned int uint32_t;
-  #endif
-# else
-  # error "Unknown compiler - please report the problems to the main simgrid mailing list (http://gforge.inria.fr/mail/?group_id=12)"
-#endif
-
-#ifndef _XBT_VISUALC_COMPILER
-  #ifndef EWOULDBLOCK
-  #define EWOULDBLOCK WSAEWOULDBLOCK
-  #endif
-
-  #ifndef EINPROGRESS
-  #define EINPROGRESS WSAEINPROGRESS
-  #endif
-
-  #ifndef ETIMEDOUT
-  #define ETIMEDOUT   WSAETIMEDOUT
-  #endif
-#endif
-
-#ifdef S_IRGRP
-  #undef S_IRGRP
-#endif
-
-#define S_IRGRP 0
-
-#ifdef S_IWGRP
-  #undef S_IWGRP
-#endif
-
-#define S_IWGRP 0
-
-#endif                          /* #ifndef __XBT_WIN32_CONFIG_H__ */
index 5e1f80c..da2a760 100644 (file)
@@ -53,7 +53,7 @@
 #if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L
 
 /* C99 says to define __STDC_LIMIT_MACROS before including stdint.h,
- * if you want the limit (max/min) macros for int types.
+ * if you want the limit (max/min) macros for int types. 
  */
 #ifndef __STDC_LIMIT_MACROS
 #define __STDC_LIMIT_MACROS 1
@@ -70,7 +70,7 @@ typedef uint32_t flex_uint32_t;
 typedef signed char flex_int8_t;
 typedef short int flex_int16_t;
 typedef int flex_int32_t;
-typedef unsigned char flex_uint8_t;
+typedef unsigned char flex_uint8_t; 
 typedef unsigned short int flex_uint16_t;
 typedef unsigned int flex_uint32_t;
 
@@ -196,7 +196,7 @@ extern FILE *xbt_automaton_parser_in, *xbt_automaton_parser_out;
 
     #define YY_LESS_LINENO(n)
     #define YY_LINENO_REWIND_TO(ptr)
-
+    
 /* Return all but the first "n" matched characters back to the input stream. */
 #define yyless(n) \
        do \
@@ -253,7 +253,7 @@ struct yy_buffer_state
 
     int yy_bs_lineno; /**< The line count. */
     int yy_bs_column; /**< The column count. */
-
+    
        /* Whether to try to fill the input buffer when we reach the
         * end of it.
         */
@@ -522,21 +522,30 @@ int xbt_automaton_parser__flex_debug = 0;
 #define YY_RESTORE_YY_MORE_OFFSET
 char *xbt_automaton_parser_text;
 #line 1 "parserPromela.lex"
-/* Copyright (c) 2012, 2014-2015. The SimGrid Team.
+/* Copyright (c) 2012, 2014. The SimGrid Team.
  * All rights reserved.                                                     */
-
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
-
 #line 10 "parserPromela.lex"
 
+#include "simgrid_config.h"
+#ifndef HAVE_UNISTD_H
+#define YY_NO_UNISTD_H /* hello Windows */
+
+#ifdef _MSC_VER
+# include <io.h>
+# include <process.h>
+# define _CRT_SECURE_NO_WARNINGS
+# define _CRT_NONSTDC_NO_WARNINGS
+#endif
+#endif
 
 #include <stdio.h>
 #include "parserPromela.tab.hacc"
-
+  
   extern YYSTYPE yylval;
-
-#line 538 "automaton_lexer.yy.c"
+#line 549 "automaton_lexer.yy.c"
 
 #define INITIAL 0
 
@@ -596,7 +605,7 @@ extern int xbt_automaton_parser_wrap (void );
 #endif
 
     static void yyunput (int c,char *buf_ptr  );
-
+    
 #ifndef yytext_ptr
 static void yy_flex_strncpy (char *,yyconst char *,int );
 #endif
@@ -719,10 +728,10 @@ extern int xbt_automaton_parser_lex (void);
  */
 YY_DECL
 {
-       yy_state_type yy_current_state;
-       char *yy_cp, *yy_bp;
-       int yy_act;
-
+       register yy_state_type yy_current_state;
+       register char *yy_cp, *yy_bp;
+       register int yy_act;
+    
        if ( !(yy_init) )
                {
                (yy_init) = 1;
@@ -750,10 +759,10 @@ YY_DECL
                }
 
        {
-#line 34 "parserPromela.lex"
+#line 45 "parserPromela.lex"
 
 
-#line 755 "automaton_lexer.yy.c"
+#line 766 "automaton_lexer.yy.c"
 
        while ( 1 )             /* loops until end-of-file is reached */
                {
@@ -771,7 +780,7 @@ YY_DECL
 yy_match:
                do
                        {
-                       YY_CHAR yy_c = yy_ec[YY_SC_TO_UI(*yy_cp)] ;
+                       register YY_CHAR yy_c = yy_ec[YY_SC_TO_UI(*yy_cp)] ;
                        if ( yy_accept[yy_current_state] )
                                {
                                (yy_last_accepting_state) = yy_current_state;
@@ -812,118 +821,118 @@ do_action:      /* This label is used only to access EOF actions. */
 
 case 1:
 YY_RULE_SETUP
-#line 36 "parserPromela.lex"
+#line 47 "parserPromela.lex"
 { return (NEVER); }
        YY_BREAK
 case 2:
 YY_RULE_SETUP
-#line 37 "parserPromela.lex"
+#line 48 "parserPromela.lex"
 { return (IF); }
        YY_BREAK
 case 3:
 YY_RULE_SETUP
-#line 38 "parserPromela.lex"
+#line 49 "parserPromela.lex"
 { return (FI); }
        YY_BREAK
 case 4:
 YY_RULE_SETUP
-#line 39 "parserPromela.lex"
+#line 50 "parserPromela.lex"
 { return (IMPLIES); }
        YY_BREAK
 case 5:
 YY_RULE_SETUP
-#line 40 "parserPromela.lex"
+#line 51 "parserPromela.lex"
 { return (GOTO); }
        YY_BREAK
 case 6:
 YY_RULE_SETUP
-#line 41 "parserPromela.lex"
+#line 52 "parserPromela.lex"
 { return (AND); }
        YY_BREAK
 case 7:
 YY_RULE_SETUP
-#line 42 "parserPromela.lex"
+#line 53 "parserPromela.lex"
 { return (OR); }
        YY_BREAK
 case 8:
 YY_RULE_SETUP
-#line 43 "parserPromela.lex"
+#line 54 "parserPromela.lex"
 { return (NOT); }
        YY_BREAK
 case 9:
 YY_RULE_SETUP
-#line 44 "parserPromela.lex"
+#line 55 "parserPromela.lex"
 { return (LEFT_PAR); }
        YY_BREAK
 case 10:
 YY_RULE_SETUP
-#line 45 "parserPromela.lex"
+#line 56 "parserPromela.lex"
 { return (RIGHT_PAR); }
        YY_BREAK
 case 11:
 YY_RULE_SETUP
-#line 46 "parserPromela.lex"
+#line 57 "parserPromela.lex"
 { return (CASE); }
        YY_BREAK
 case 12:
 YY_RULE_SETUP
-#line 47 "parserPromela.lex"
+#line 58 "parserPromela.lex"
 { return (COLON); }
        YY_BREAK
 case 13:
 YY_RULE_SETUP
-#line 48 "parserPromela.lex"
+#line 59 "parserPromela.lex"
 { return (SEMI_COLON); }
        YY_BREAK
 case 14:
 YY_RULE_SETUP
-#line 49 "parserPromela.lex"
+#line 60 "parserPromela.lex"
 { return (CASE_TRUE); }
        YY_BREAK
 case 15:
 YY_RULE_SETUP
-#line 50 "parserPromela.lex"
+#line 61 "parserPromela.lex"
 { return (LEFT_BRACE); }
        YY_BREAK
 case 16:
 YY_RULE_SETUP
-#line 51 "parserPromela.lex"
+#line 62 "parserPromela.lex"
 { return (RIGHT_BRACE); }
        YY_BREAK
 case 17:
 /* rule 17 can match eol */
 YY_RULE_SETUP
-#line 54 "parserPromela.lex"
+#line 65 "parserPromela.lex"
 { }
        YY_BREAK
 case 18:
 YY_RULE_SETUP
-#line 56 "parserPromela.lex"
+#line 67 "parserPromela.lex"
 { }
        YY_BREAK
 case 19:
 YY_RULE_SETUP
-#line 59 "parserPromela.lex"
-{ sscanf(xbt_automaton_parser_text,"%lf",&yylval.real);
+#line 70 "parserPromela.lex"
+{ sscanf(xbt_automaton_parser_text,"%lf",&yylval.real); 
                             return (LITT_REEL); }
        YY_BREAK
 case 20:
 YY_RULE_SETUP
-#line 62 "parserPromela.lex"
-{ sscanf(xbt_automaton_parser_text,"%d",&yylval.integer);
+#line 73 "parserPromela.lex"
+{ sscanf(xbt_automaton_parser_text,"%d",&yylval.integer); 
                             return (LITT_ENT); }
        YY_BREAK
 case 21:
 /* rule 21 can match eol */
 YY_RULE_SETUP
-#line 65 "parserPromela.lex"
+#line 76 "parserPromela.lex"
 { yylval.string=(char *)malloc(strlen(xbt_automaton_parser_text)+1);
-                            sscanf(xbt_automaton_parser_text,"%s",yylval.string);
+                            sscanf(xbt_automaton_parser_text,"%s",yylval.string); 
                             return (LITT_CHAINE); }
        YY_BREAK
 case 22:
 YY_RULE_SETUP
-#line 69 "parserPromela.lex"
+#line 80 "parserPromela.lex"
 { yylval.string=(char *)malloc(strlen(xbt_automaton_parser_text)+1);
                             sscanf(xbt_automaton_parser_text,"%s",yylval.string);
                                              return (ID); }
@@ -931,20 +940,20 @@ YY_RULE_SETUP
 case 23:
 /* rule 23 can match eol */
 YY_RULE_SETUP
-#line 73 "parserPromela.lex"
+#line 84 "parserPromela.lex"
 { }
        YY_BREAK
 case 24:
 YY_RULE_SETUP
-#line 75 "parserPromela.lex"
+#line 86 "parserPromela.lex"
 { }
        YY_BREAK
 case 25:
 YY_RULE_SETUP
-#line 77 "parserPromela.lex"
+#line 88 "parserPromela.lex"
 ECHO;
        YY_BREAK
-#line 946 "automaton_lexer.yy.c"
+#line 957 "automaton_lexer.yy.c"
 case YY_STATE_EOF(INITIAL):
        yyterminate();
 
@@ -1087,9 +1096,9 @@ case YY_STATE_EOF(INITIAL):
  */
 static int yy_get_next_buffer (void)
 {
-       char *dest = YY_CURRENT_BUFFER_LVALUE->yy_ch_buf;
-       char *source = (yytext_ptr);
-       int number_to_move, i;
+       register char *dest = YY_CURRENT_BUFFER_LVALUE->yy_ch_buf;
+       register char *source = (yytext_ptr);
+       register int number_to_move, i;
        int ret_val;
 
        if ( (yy_c_buf_p) > &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] )
@@ -1221,14 +1230,14 @@ static int yy_get_next_buffer (void)
 
     static yy_state_type yy_get_previous_state (void)
 {
-       yy_state_type yy_current_state;
-       char *yy_cp;
-
+       register yy_state_type yy_current_state;
+       register char *yy_cp;
+    
        yy_current_state = (yy_start);
 
        for ( yy_cp = (yytext_ptr) + YY_MORE_ADJ; yy_cp < (yy_c_buf_p); ++yy_cp )
                {
-               YY_CHAR yy_c = (*yy_cp ? yy_ec[YY_SC_TO_UI(*yy_cp)] : 1);
+               register YY_CHAR yy_c = (*yy_cp ? yy_ec[YY_SC_TO_UI(*yy_cp)] : 1);
                if ( yy_accept[yy_current_state] )
                        {
                        (yy_last_accepting_state) = yy_current_state;
@@ -1253,10 +1262,10 @@ static int yy_get_next_buffer (void)
  */
     static yy_state_type yy_try_NUL_trans  (yy_state_type yy_current_state )
 {
-       int yy_is_jam;
-       char *yy_cp = (yy_c_buf_p);
+       register int yy_is_jam;
+       register char *yy_cp = (yy_c_buf_p);
 
-       YY_CHAR yy_c = 1;
+       register YY_CHAR yy_c = 1;
        if ( yy_accept[yy_current_state] )
                {
                (yy_last_accepting_state) = yy_current_state;
@@ -1274,10 +1283,10 @@ static int yy_get_next_buffer (void)
                return yy_is_jam ? 0 : yy_current_state;
 }
 
-    static void yyunput (int c, char * yy_bp )
+    static void yyunput (int c, register char * yy_bp )
 {
-       char *yy_cp;
-
+       register char *yy_cp;
+    
     yy_cp = (yy_c_buf_p);
 
        /* undo effects of setting up xbt_automaton_parser_text */
@@ -1286,10 +1295,10 @@ static int yy_get_next_buffer (void)
        if ( yy_cp < YY_CURRENT_BUFFER_LVALUE->yy_ch_buf + 2 )
                { /* need to shift things up to make room */
                /* +2 for EOB chars. */
-               yy_size_t number_to_move = (yy_n_chars) + 2;
-               char *dest = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[
+               register yy_size_t number_to_move = (yy_n_chars) + 2;
+               register char *dest = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[
                                        YY_CURRENT_BUFFER_LVALUE->yy_buf_size + 2];
-               char *source =
+               register char *source =
                                &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[number_to_move];
 
                while ( source > YY_CURRENT_BUFFER_LVALUE->yy_ch_buf )
@@ -1320,7 +1329,7 @@ static int yy_get_next_buffer (void)
 
 {
        int c;
-
+    
        *(yy_c_buf_p) = (yy_hold_char);
 
        if ( *(yy_c_buf_p) == YY_END_OF_BUFFER_CHAR )
@@ -1387,12 +1396,12 @@ static int yy_get_next_buffer (void)
 
 /** Immediately switch to a different input stream.
  * @param input_file A readable stream.
- *
+ * 
  * @note This function does not reset the start condition to @c INITIAL .
  */
     void xbt_automaton_parser_restart  (FILE * input_file )
 {
-
+    
        if ( ! YY_CURRENT_BUFFER ){
         xbt_automaton_parser_ensure_buffer_stack ();
                YY_CURRENT_BUFFER_LVALUE =
@@ -1405,11 +1414,11 @@ static int yy_get_next_buffer (void)
 
 /** Switch to a different input buffer.
  * @param new_buffer The new input buffer.
- *
+ * 
  */
     void xbt_automaton_parser__switch_to_buffer  (YY_BUFFER_STATE  new_buffer )
 {
-
+    
        /* TODO. We should be able to replace this entire function body
         * with
         *              xbt_automaton_parser_pop_buffer_state();
@@ -1449,13 +1458,13 @@ static void xbt_automaton_parser__load_buffer_state  (void)
 /** Allocate and initialize an input buffer state.
  * @param file A readable stream.
  * @param size The character buffer size in bytes. When in doubt, use @c YY_BUF_SIZE.
- *
+ * 
  * @return the allocated buffer state.
  */
     YY_BUFFER_STATE xbt_automaton_parser__create_buffer  (FILE * file, int  size )
 {
        YY_BUFFER_STATE b;
-
+    
        b = (YY_BUFFER_STATE) xbt_automaton_parser_alloc(sizeof( struct yy_buffer_state )  );
        if ( ! b )
                YY_FATAL_ERROR( "out of dynamic memory in xbt_automaton_parser__create_buffer()" );
@@ -1478,11 +1487,11 @@ static void xbt_automaton_parser__load_buffer_state  (void)
 
 /** Destroy the buffer.
  * @param b a buffer created with xbt_automaton_parser__create_buffer()
- *
+ * 
  */
     void xbt_automaton_parser__delete_buffer (YY_BUFFER_STATE  b )
 {
-
+    
        if ( ! b )
                return;
 
@@ -1503,7 +1512,7 @@ static void xbt_automaton_parser__load_buffer_state  (void)
 
 {
        int oerrno = errno;
-
+    
        xbt_automaton_parser__flush_buffer(b );
 
        b->yy_input_file = file;
@@ -1519,13 +1528,13 @@ static void xbt_automaton_parser__load_buffer_state  (void)
     }
 
         b->yy_is_interactive = file ? (isatty( fileno(file) ) > 0) : 0;
-
+    
        errno = oerrno;
 }
 
 /** Discard all buffered characters. On the next scan, YY_INPUT will be called.
  * @param b the buffer state to be flushed, usually @c YY_CURRENT_BUFFER.
- *
+ * 
  */
     void xbt_automaton_parser__flush_buffer (YY_BUFFER_STATE  b )
 {
@@ -1554,7 +1563,7 @@ static void xbt_automaton_parser__load_buffer_state  (void)
  *  the current state. This function will allocate the stack
  *  if necessary.
  *  @param new_buffer The new state.
- *
+ *  
  */
 void xbt_automaton_parser_push_buffer_state (YY_BUFFER_STATE new_buffer )
 {
@@ -1584,7 +1593,7 @@ void xbt_automaton_parser_push_buffer_state (YY_BUFFER_STATE new_buffer )
 
 /** Removes and deletes the top of the stack, if present.
  *  The next element becomes the new top.
- *
+ *  
  */
 void xbt_automaton_parser_pop_buffer_state (void)
 {
@@ -1608,7 +1617,7 @@ void xbt_automaton_parser_pop_buffer_state (void)
 static void xbt_automaton_parser_ensure_buffer_stack (void)
 {
        yy_size_t num_to_alloc;
-
+    
        if (!(yy_buffer_stack)) {
 
                /* First allocation is just for 2 elements, since we don't know if this
@@ -1621,9 +1630,9 @@ static void xbt_automaton_parser_ensure_buffer_stack (void)
                                                                );
                if ( ! (yy_buffer_stack) )
                        YY_FATAL_ERROR( "out of dynamic memory in xbt_automaton_parser_ensure_buffer_stack()" );
-
+                                                                 
                memset((yy_buffer_stack), 0, num_to_alloc * sizeof(struct yy_buffer_state*));
-
+                               
                (yy_buffer_stack_max) = num_to_alloc;
                (yy_buffer_stack_top) = 0;
                return;
@@ -1651,13 +1660,13 @@ static void xbt_automaton_parser_ensure_buffer_stack (void)
 /** Setup the input buffer state to scan directly from a user-specified character buffer.
  * @param base the character buffer
  * @param size the size in bytes of the character buffer
- *
- * @return the newly allocated buffer state object.
+ * 
+ * @return the newly allocated buffer state object. 
  */
 YY_BUFFER_STATE xbt_automaton_parser__scan_buffer  (char * base, yy_size_t  size )
 {
        YY_BUFFER_STATE b;
-
+    
        if ( size < 2 ||
             base[size-2] != YY_END_OF_BUFFER_CHAR ||
             base[size-1] != YY_END_OF_BUFFER_CHAR )
@@ -1686,14 +1695,14 @@ YY_BUFFER_STATE xbt_automaton_parser__scan_buffer  (char * base, yy_size_t  size
 /** Setup the input buffer state to scan a string. The next call to xbt_automaton_parser_lex() will
  * scan from a @e copy of @a str.
  * @param yystr a NUL-terminated string to scan
- *
+ * 
  * @return the newly allocated buffer state object.
  * @note If you want to scan bytes that may contain NUL values, then use
  *       xbt_automaton_parser__scan_bytes() instead.
  */
 YY_BUFFER_STATE xbt_automaton_parser__scan_string (yyconst char * yystr )
 {
-
+    
        return xbt_automaton_parser__scan_bytes(yystr,strlen(yystr) );
 }
 
@@ -1701,7 +1710,7 @@ YY_BUFFER_STATE xbt_automaton_parser__scan_string (yyconst char * yystr )
  * scan from a @e copy of @a bytes.
  * @param yybytes the byte buffer to scan
  * @param _yybytes_len the number of bytes in the buffer pointed to by @a bytes.
- *
+ * 
  * @return the newly allocated buffer state object.
  */
 YY_BUFFER_STATE xbt_automaton_parser__scan_bytes  (yyconst char * yybytes, yy_size_t  _yybytes_len )
@@ -1710,7 +1719,7 @@ YY_BUFFER_STATE xbt_automaton_parser__scan_bytes  (yyconst char * yybytes, yy_si
        char *buf;
        yy_size_t n;
        yy_size_t i;
-
+    
        /* Get memory for full buffer, including space for trailing EOB's. */
        n = _yybytes_len + 2;
        buf = (char *) xbt_automaton_parser_alloc(n  );
@@ -1764,16 +1773,16 @@ static void yy_fatal_error (yyconst char* msg )
 /* Accessor  methods (get/set functions) to struct members. */
 
 /** Get the current line number.
- *
+ * 
  */
 int xbt_automaton_parser_get_lineno  (void)
 {
-
+        
     return xbt_automaton_parser_lineno;
 }
 
 /** Get the input stream.
- *
+ * 
  */
 FILE *xbt_automaton_parser_get_in  (void)
 {
@@ -1781,7 +1790,7 @@ FILE *xbt_automaton_parser_get_in  (void)
 }
 
 /** Get the output stream.
- *
+ * 
  */
 FILE *xbt_automaton_parser_get_out  (void)
 {
@@ -1789,7 +1798,7 @@ FILE *xbt_automaton_parser_get_out  (void)
 }
 
 /** Get the length of the current token.
- *
+ * 
  */
 yy_size_t xbt_automaton_parser_get_leng  (void)
 {
@@ -1797,7 +1806,7 @@ yy_size_t xbt_automaton_parser_get_leng  (void)
 }
 
 /** Get the current token.
- *
+ * 
  */
 
 char *xbt_automaton_parser_get_text  (void)
@@ -1807,18 +1816,18 @@ char *xbt_automaton_parser_get_text  (void)
 
 /** Set the current line number.
  * @param line_number
- *
+ * 
  */
 void xbt_automaton_parser_set_lineno (int  line_number )
 {
-
+    
     xbt_automaton_parser_lineno = line_number;
 }
 
 /** Set the input stream. This does not discard the current
  * input buffer.
  * @param in_str A readable stream.
- *
+ * 
  * @see xbt_automaton_parser__switch_to_buffer
  */
 void xbt_automaton_parser_set_in (FILE *  in_str )
@@ -1872,7 +1881,7 @@ static int yy_init_globals (void)
 /* xbt_automaton_parser_lex_destroy is for both reentrant and non-reentrant scanners. */
 int xbt_automaton_parser_lex_destroy  (void)
 {
-
+    
     /* Pop the buffer stack, destroying each element. */
        while(YY_CURRENT_BUFFER){
                xbt_automaton_parser__delete_buffer(YY_CURRENT_BUFFER  );
@@ -1898,7 +1907,7 @@ int xbt_automaton_parser_lex_destroy  (void)
 #ifndef yytext_ptr
 static void yy_flex_strncpy (char* s1, yyconst char * s2, int n )
 {
-       int i;
+       register int i;
        for ( i = 0; i < n; ++i )
                s1[i] = s2[i];
 }
@@ -1907,7 +1916,7 @@ static void yy_flex_strncpy (char* s1, yyconst char * s2, int n )
 #ifdef YY_NEED_STRLEN
 static int yy_flex_strlen (yyconst char * s )
 {
-       int n;
+       register int n;
        for ( n = 0; s[n]; ++n )
                ;
 
@@ -1939,7 +1948,7 @@ void xbt_automaton_parser_free (void * ptr )
 
 #define YYTABLES_NAME "yytables"
 
-#line 76 "parserPromela.lex"
+#line 87 "parserPromela.lex"
 
 
 
index 2be47f2..b93895b 100644 (file)
@@ -8,6 +8,17 @@
 
 %{
 
+#include "simgrid_config.h"
+#ifndef HAVE_UNISTD_H
+#define YY_NO_UNISTD_H /* hello Windows */
+
+#ifdef _MSC_VER
+# include <io.h>
+# include <process.h>
+# define _CRT_SECURE_NO_WARNINGS
+# define _CRT_NONSTDC_NO_WARNINGS
+#endif
+#endif
 
 #include <stdio.h>
 #include "parserPromela.tab.hacc"
index 898e1e4..67892ec 100644 (file)
 /* Copy the first part of user declarations.  */
 #line 7 "parserPromela.yacc" /* yacc.c:339  */
 
+#include "simgrid_config.h"
+#ifndef HAVE_UNISTD_H
+#define YY_NO_UNISTD_H /* hello Windows */
+#endif
 
 #include "automaton_lexer.yy.c"
 #include <xbt/automaton.h>
@@ -79,7 +83,7 @@
 void yyerror(const char *s);
 
 
-#line 83 "parserPromela.tab.cacc" /* yacc.c:339  */
+#line 87 "parserPromela.tab.cacc" /* yacc.c:339  */
 
 # ifndef YY_NULLPTR
 #  if defined __cplusplus && 201103L <= __cplusplus
@@ -142,14 +146,14 @@ extern int xbt_automaton_parser_debug;
 typedef union YYSTYPE YYSTYPE;
 union YYSTYPE
 {
-#line 16 "parserPromela.yacc" /* yacc.c:355  */
+#line 20 "parserPromela.yacc" /* yacc.c:355  */
 
   double real;
   int integer;
   char* string;
   xbt_automaton_exp_label_t label;
 
-#line 153 "parserPromela.tab.cacc" /* yacc.c:355  */
+#line 157 "parserPromela.tab.cacc" /* yacc.c:355  */
 };
 # define YYSTYPE_IS_TRIVIAL 1
 # define YYSTYPE_IS_DECLARED 1
@@ -164,7 +168,7 @@ int xbt_automaton_parser_parse (void);
 
 /* Copy the second part of user declarations.  */
 
-#line 168 "parserPromela.tab.cacc" /* yacc.c:358  */
+#line 172 "parserPromela.tab.cacc" /* yacc.c:358  */
 
 #ifdef short
 # undef short
@@ -463,8 +467,8 @@ static const yytype_uint8 yytranslate[] =
   /* YYRLINE[YYN] -- Source line where rule number YYN was defined.  */
 static const yytype_uint8 yyrline[] =
 {
-       0,    53,    53,    56,    57,    57,    60,    61,    64,    65,
-      66,    67,    68,    69
+       0,    57,    57,    60,    61,    61,    64,    65,    68,    69,
+      70,    71,    72,    73
 };
 #endif
 
@@ -1250,55 +1254,55 @@ yyreduce:
   switch (yyn)
     {
         case 4:
-#line 57 "parserPromela.yacc" /* yacc.c:1646  */
+#line 61 "parserPromela.yacc" /* yacc.c:1646  */
     { new_state((yyvsp[-1].string), 1);}
-#line 1256 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1260 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 7:
-#line 61 "parserPromela.yacc" /* yacc.c:1646  */
+#line 65 "parserPromela.yacc" /* yacc.c:1646  */
     { new_transition((yyvsp[-1].string), (yyvsp[-4].label));}
-#line 1262 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1266 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 8:
-#line 64 "parserPromela.yacc" /* yacc.c:1646  */
+#line 68 "parserPromela.yacc" /* yacc.c:1646  */
     { (yyval.label) = (yyvsp[-1].label); }
-#line 1268 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1272 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 9:
-#line 65 "parserPromela.yacc" /* yacc.c:1646  */
+#line 69 "parserPromela.yacc" /* yacc.c:1646  */
     { (yyval.label) = new_label(0, (yyvsp[-2].label), (yyvsp[0].label)); }
-#line 1274 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1278 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 10:
-#line 66 "parserPromela.yacc" /* yacc.c:1646  */
+#line 70 "parserPromela.yacc" /* yacc.c:1646  */
     { (yyval.label) = new_label(1, (yyvsp[-2].label), (yyvsp[0].label)); }
-#line 1280 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1284 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 11:
-#line 67 "parserPromela.yacc" /* yacc.c:1646  */
+#line 71 "parserPromela.yacc" /* yacc.c:1646  */
     { (yyval.label) = new_label(2, (yyvsp[0].label)); }
-#line 1286 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1290 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 12:
-#line 68 "parserPromela.yacc" /* yacc.c:1646  */
+#line 72 "parserPromela.yacc" /* yacc.c:1646  */
     { (yyval.label) = new_label(4); }
-#line 1292 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1296 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
   case 13:
-#line 69 "parserPromela.yacc" /* yacc.c:1646  */
+#line 73 "parserPromela.yacc" /* yacc.c:1646  */
     { (yyval.label) = new_label(3, (yyvsp[0].string)); }
-#line 1298 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1302 "parserPromela.tab.cacc" /* yacc.c:1646  */
     break;
 
 
-#line 1302 "parserPromela.tab.cacc" /* yacc.c:1646  */
+#line 1306 "parserPromela.tab.cacc" /* yacc.c:1646  */
       default: break;
     }
   /* User semantic actions sometimes alter yychar, and that requires
@@ -1526,7 +1530,7 @@ yyreturn:
 #endif
   return yyresult;
 }
-#line 72 "parserPromela.yacc" /* yacc.c:1906  */
+#line 76 "parserPromela.yacc" /* yacc.c:1906  */
 
 
 
index 587506e..bfab886 100644 (file)
@@ -73,7 +73,7 @@ extern int xbt_automaton_parser_debug;
 typedef union YYSTYPE YYSTYPE;
 union YYSTYPE
 {
-#line 16 "parserPromela.yacc" /* yacc.c:1909  */
+#line 20 "parserPromela.yacc" /* yacc.c:1909  */
 
   double real;
   int integer;
index 57468b6..d5789f0 100644 (file)
@@ -5,6 +5,10 @@
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
 %{
+#include "simgrid_config.h"
+#ifndef HAVE_UNISTD_H
+#define YY_NO_UNISTD_H /* hello Windows */
+#endif
 
 #include "automaton_lexer.yy.c"
 #include <xbt/automaton.h>
index 69389e7..3f8a5e4 100644 (file)
@@ -8,7 +8,6 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include <stdio.h>
 #include "xbt/misc.h"
 #include "xbt/sysdep.h"
 #include "xbt/log.h"
@@ -17,6 +16,8 @@
 #include "xbt/dict.h"
 #include "xbt/peer.h"
 
+#include <stdio.h>
+
 #include "xbt/config.h"         /* prototypes of this module */
 
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(xbt_cfg, xbt, "configuration support");
index d7e8765..674b7b4 100644 (file)
@@ -824,7 +824,7 @@ static void count_check_get_key(xbt_dict_t dict, int length)
 {
   xbt_dict_cursor_t cursor;
   char *key;
-  _XBT_GNUC_UNUSED char *key2;
+  XBT_ATTRIB_UNUSED char *key2;
   void *data;
   int effective = 0;
 
index 34eb4d0..7db9869 100644 (file)
@@ -10,6 +10,7 @@
 #ifndef _XBT_DICT_PRIVATE_H__
 #define _XBT_DICT_PRIVATE_H__
 
+#include "xbt/base.h"
 #include "xbt/sysdep.h"
 #include "xbt/log.h"
 #include "xbt/ex.h"
@@ -36,22 +37,22 @@ typedef struct s_xbt_dict {
 
 typedef struct s_xbt_dict_cursor s_xbt_dict_cursor_t;
 
-extern xbt_mallocator_t dict_elm_mallocator;
-extern void *dict_elm_mallocator_new_f(void);
+extern XBT_PRIVATE xbt_mallocator_t dict_elm_mallocator;
+XBT_PRIVATE void * dict_elm_mallocator_new_f(void);
 #define dict_elm_mallocator_free_f xbt_free_f
 #define dict_elm_mallocator_reset_f ((void_f_pvoid_t)NULL)
 
-extern xbt_mallocator_t dict_het_elm_mallocator;
-extern void *dict_het_elm_mallocator_new_f(void);
+extern XBT_PRIVATE xbt_mallocator_t dict_het_elm_mallocator;
+extern XBT_PRIVATE void * dict_het_elm_mallocator_new_f(void);
 #define dict_het_elm_mallocator_free_f xbt_free_f
 #define dict_het_elm_mallocator_reset_f ((void_f_pvoid_t)NULL)
 
 /*####[ Function prototypes ]################################################*/
-xbt_dictelm_t xbt_dictelm_new(xbt_dict_t dict, const char *key, int key_len,
+XBT_PRIVATE xbt_dictelm_t xbt_dictelm_new(xbt_dict_t dict, const char *key, int key_len,
                               unsigned int hash_code, void *content,
                               void_f_pvoid_t free_f);
-void xbt_dictelm_free(xbt_dict_t dict, xbt_dictelm_t element);
-void xbt_dictelm_set_data(xbt_dict_t dict, xbt_dictelm_t element,
+XBT_PRIVATE void xbt_dictelm_free(xbt_dict_t dict, xbt_dictelm_t element);
+XBT_PRIVATE void xbt_dictelm_set_data(xbt_dict_t dict, xbt_dictelm_t element,
                           void *data, void_f_pvoid_t free_ctn);
 
 #endif                          /* _XBT_DICT_PRIVATE_H_ */
index 25de69f..28c6efc 100644 (file)
@@ -27,7 +27,7 @@ static XBT_INLINE void _sanity_check_idx(int idx)
 
 static XBT_INLINE void _check_inbound_idx(xbt_dynar_t dynar, int idx)
 {
-  if (idx < 0 || idx >= dynar->used) {
+  if (idx < 0 || idx >= (int)dynar->used) {
     THROWF(bound_error, idx,
            "dynar is not that long. You asked %d, but it's only %lu long",
            (int) (idx), (unsigned long) dynar->used);
index 0cd35b8..a54869f 100644 (file)
@@ -148,6 +148,11 @@ void xbt_ex_display(xbt_ex_t * e)
   XBT_CRITICAL("%s", e->msg);
   xbt_free(thrower);
 
+  if (xbt_initialized==0 || smx_cleaned) {
+         fprintf(stderr, "Ouch. SimGrid is not initialized yet, or already closing. No backtrace available.\n");
+         return; /* Not started yet or already closing. Trying to generate a backtrace would probably fail */
+  }
+
   if (!e->bt_strings)
     xbt_ex_setup_backtrace(e);
 
@@ -333,7 +338,7 @@ XBT_TEST_UNIT("variables", test_variables, "variable value preservation")
 {
   xbt_ex_t ex;
   int r1;
-  int _XBT_GNUC_UNUSED r2;
+  int XBT_ATTRIB_UNUSED r2;
   int v1;
   volatile int v2;
 
index 4f510f6..cef5284 100644 (file)
 #ifndef _XBT_EX_INTERFACE_H_
 #define _XBT_EX_INTERFACE_H_
 
+#include "xbt/base.h"
 #include "xbt/ex.h"
 
 /* Change raw libc symbols to file names and line numbers */
-void xbt_ex_setup_backtrace(xbt_ex_t * e);
+XBT_PRIVATE void xbt_ex_setup_backtrace(xbt_ex_t * e);
 
 #endif                          /* _XBT_EX_INTERFACE_H_ */
index 52bed43..1db1686 100644 (file)
@@ -6,8 +6,6 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
-#include <errno.h>
-#include <stdlib.h>
 #include "xbt/sysdep.h"
 #include "xbt/log.h"
 #include "xbt/graph.h"
 #include "xbt/dict.h"
 #include "xbt/heap.h"
 #include "xbt/str.h"
+#include "xbt/file.h"
 
-
+#include <errno.h>
+#include <stdlib.h>
 
 
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(xbt_graph, xbt, "Graph");
@@ -627,7 +627,7 @@ xbt_graph_t xbt_graph_read(const char *filename,
   ETag_graphxml_edge_fun = __parse_edge;
 
   xbt_graph_parse_open(filename);
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   res = xbt_graph_parse();
   xbt_assert(!res, "Parse error in %s", filename);
   xbt_graph_parse_close();
index 819a11f..aa85f24 100644 (file)
@@ -6,6 +6,8 @@
 
 #ifndef _XBT_GRAPH_PRIVATE_H
 #define _XBT_GRAPH_PRIVATE_H
+
+#include "xbt/base.h"
 #include "xbt/dynar.h"
 #include "xbt/graph.h"
 
@@ -13,9 +15,9 @@
 #define CURRENTLY_EXPLORING 1
 #define ALREADY_EXPLORED 2
 
-void xbt_floyd_algorithm(xbt_graph_t g, double *adj, double *d,
+XBT_PRIVATE void xbt_floyd_algorithm(xbt_graph_t g, double *adj, double *d,
                          xbt_node_t * p);
-void xbt_graph_depth_visit(xbt_graph_t g, xbt_node_t n,
+XBT_PRIVATE void xbt_graph_depth_visit(xbt_graph_t g, xbt_node_t n,
                            xbt_node_t * sorted, int *idx);
 
 #endif                          /* _XBT_GRAPH_PRIVATE_H */
index d143e32..4f7605d 100644 (file)
@@ -123,7 +123,7 @@ int_f_void_t xbt_graph_parse = _xbt_graph_parse;
 double xbt_graph_parse_get_double(const char *string)
 {
   double result;
-  _XBT_GNUC_UNUSED int ret = 0;
+  XBT_ATTRIB_UNUSED int ret = 0;
 
   ret = sscanf(string, "%lg", &result);
   xbt_assert((ret == 1), "Parse error line %d : %s not a number",
index 8490906..621ff10 100644 (file)
@@ -359,7 +359,7 @@ void mmalloc_postexit(void)
 size_t mmalloc_get_bytes_used_remote(size_t heaplimit, const malloc_info* heapinfo)
 {
   int bytes = 0;
-  for (size_t i=0; i<=heaplimit; ++i){
+  for (size_t i=0; i < heaplimit; ++i){
     if (heapinfo[i].type == MMALLOC_TYPE_UNFRAGMENTED){
       if (heapinfo[i].busy_block.busy_size > 0)
         bytes += heapinfo[i].busy_block.busy_size;
index cb488ac..12441e7 100644 (file)
@@ -14,6 +14,7 @@
 #ifndef __MMPRIVATE_H
 #define __MMPRIVATE_H 1
 
+#include <xbt/base.h>
 #include <xbt/misc.h>
 
 #include "portable.h"
@@ -323,14 +324,14 @@ static inline int mmalloc_get_increment(malloc_info* heapinfo) {
   }
 }
 
-void mmcheck(xbt_mheap_t heap);
+XBT_PRIVATE void mmcheck(xbt_mheap_t heap);
 
-int malloc_use_mmalloc(void);
+XBT_PRIVATE int malloc_use_mmalloc(void);
 
-int mmalloc_exec_using_mm(int argc, const char** argv);
-void mmalloc_ensure_using_mm(int argc, const char** argv);
+XBT_PRIVATE int mmalloc_exec_using_mm(int argc, const char** argv);
+XBT_PRIVATE void mmalloc_ensure_using_mm(int argc, const char** argv);
 
-size_t mmalloc_get_bytes_used_remote(size_t heaplimit, const malloc_info* heapinfo);
+XBT_PRIVATE size_t mmalloc_get_bytes_used_remote(size_t heaplimit, const malloc_info* heapinfo);
 
 SG_END_DECL()
 
similarity index 97%
rename from src/xbt/parmap.c
rename to src/xbt/parmap.cpp
index b5d9025..b30d67d 100644 (file)
@@ -4,8 +4,12 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include <atomic>
+
 #include "internal_config.h"
+#ifdef HAVE_UNISTD_H
 #include <unistd.h>
+#endif
 
 #ifndef _XBT_WIN32
 #include <sys/syscall.h>
@@ -49,10 +53,12 @@ static void futex_wait(unsigned *uaddr, unsigned val);
 static void futex_wake(unsigned *uaddr, unsigned val);
 #endif
 
+#ifndef _MSC_VER
 static void xbt_parmap_busy_master_wait(xbt_parmap_t parmap);
 static void xbt_parmap_busy_worker_signal(xbt_parmap_t parmap);
 static void xbt_parmap_busy_master_signal(xbt_parmap_t parmap);
 static void xbt_parmap_busy_worker_wait(xbt_parmap_t parmap, unsigned round);
+#endif
 
 #ifdef HAVE_MC
 static void xbt_parmap_mc_work(xbt_parmap_t parmap, int worker_id);
@@ -71,7 +77,7 @@ typedef struct s_xbt_parmap {
   xbt_os_thread_t *workers;        /**< worker thread handlers */
   void_f_pvoid_t fun;              /**< function to run in parallel on each element of data */
   xbt_dynar_t data;                /**< parameters to pass to fun in parallel */
-  unsigned int index;              /**< index of the next element of data to pick */
+  std::atomic<unsigned int> index; /**< index of the next element of data to pick */
 
 #ifdef HAVE_MC
   int finish;
@@ -118,7 +124,7 @@ xbt_parmap_t xbt_parmap_new(unsigned int num_workers, e_xbt_parmap_mode_t mode)
   XBT_DEBUG("Create new parmap (%u workers)", num_workers);
 
   /* Initialize the thread pool data structure */
-  xbt_parmap_t parmap = xbt_new0(s_xbt_parmap_t, 1);
+  xbt_parmap_t parmap = new s_xbt_parmap_t();
   parmap->workers = xbt_new(xbt_os_thread_t, num_workers);
 
   parmap->num_workers = num_workers;
@@ -163,7 +169,7 @@ xbt_parmap_t xbt_parmap_mc_new(unsigned int num_workers, e_xbt_parmap_mode_t mod
   XBT_DEBUG("Create new parmap (%u workers)", num_workers);
 
   /* Initialize the thread pool data structure */
-  xbt_parmap_t parmap = xbt_new0(s_xbt_parmap_t, 1);
+  xbt_parmap_t parmap = new s_xbt_parmap_t();
   parmap->workers = xbt_new(xbt_os_thread_t, num_workers);
 
   parmap->num_workers = num_workers;
@@ -207,7 +213,7 @@ void xbt_parmap_destroy(xbt_parmap_t parmap)
   xbt_os_mutex_destroy(parmap->done_mutex);
 
   xbt_free(parmap->workers);
-  xbt_free(parmap);
+  delete parmap;
 }
 
 /**
@@ -258,6 +264,7 @@ static void xbt_parmap_set_mode(xbt_parmap_t parmap, e_xbt_parmap_mode_t mode)
 #endif
 
     case XBT_PARMAP_BUSY_WAIT:
+#ifndef _MSC_VER
       parmap->master_wait_f = xbt_parmap_busy_master_wait;
       parmap->worker_signal_f = xbt_parmap_busy_worker_signal;
       parmap->master_signal_f = xbt_parmap_busy_master_signal;
@@ -268,6 +275,9 @@ static void xbt_parmap_set_mode(xbt_parmap_t parmap, e_xbt_parmap_mode_t mode)
       xbt_os_cond_destroy(parmap->done_cond);
       xbt_os_mutex_destroy(parmap->done_mutex);
       break;
+#else
+      xbt_die("Busy waiting not implemented on Windows yet.");
+#endif
 
     case XBT_PARMAP_DEFAULT:
       THROW_IMPOSSIBLE;
@@ -302,7 +312,7 @@ void xbt_parmap_apply(xbt_parmap_t parmap, void_f_pvoid_t fun, xbt_dynar_t data)
  */
 void* xbt_parmap_next(xbt_parmap_t parmap)
 {
-  unsigned int index = __sync_fetch_and_add(&parmap->index, 1);
+  unsigned int index = parmap->index++;
   if (index < xbt_dynar_length(parmap->data)) {
     return xbt_dynar_get_as(parmap->data, index, void*);
   }
@@ -312,7 +322,7 @@ void* xbt_parmap_next(xbt_parmap_t parmap)
 static void xbt_parmap_work(xbt_parmap_t parmap)
 {
   unsigned index;
-  while ((index = __sync_fetch_and_add(&parmap->index, 1))
+  while ((index = parmap->index++)
          < xbt_dynar_length(parmap->data))
     parmap->fun(xbt_dynar_get_as(parmap->data, index, void*));
 }
@@ -589,6 +599,7 @@ static void xbt_parmap_futex_worker_wait(xbt_parmap_t parmap, unsigned round)
 }
 #endif
 
+#ifndef _MSC_VER
 /**
  * \brief Starts the parmap: waits for all workers to be ready and returns.
  *
@@ -644,3 +655,4 @@ static void xbt_parmap_busy_worker_wait(xbt_parmap_t parmap, unsigned round)
     xbt_os_thread_yield();
   }
 }
+#endif /* ! _MSC_VER */
index 2b0ec89..8dbf6ec 100644 (file)
@@ -201,7 +201,7 @@ void xbt_setset_set_reset(xbt_setset_set_t set)
  */
 void *xbt_setset_set_choose(xbt_setset_set_t set)
 {
-  int i;
+  unsigned int i;
   /* Traverse the set and return the first element */
   for (i = 0; i < set->size; i++)
     if (set->bitmap[i] != 0)
@@ -243,7 +243,8 @@ int xbt_setset_set_belongs(xbt_setset_set_t set, void *obj)
 
 int xbt_setset_set_size(xbt_setset_set_t set)
 {
-  int i, count = 0;
+  unsigned int i;
+  int count = 0;
 
   for (i = 0; i < set->size; i++)
     count += bitcount(set->bitmap[i]);
@@ -260,7 +261,7 @@ int xbt_setset_set_size(xbt_setset_set_t set)
  */
 void xbt_setset_add(xbt_setset_set_t set1, xbt_setset_set_t set2)
 {
-  int i;
+  unsigned int i;
 
   /* Increase the size of set1 if necessary */
   if (set1->size < set2->size) {
@@ -283,7 +284,7 @@ void xbt_setset_add(xbt_setset_set_t set1, xbt_setset_set_t set2)
  */
 void xbt_setset_substract(xbt_setset_set_t set1, xbt_setset_set_t set2)
 {
-  int i;
+  unsigned int i;
 
   for (i = 0; i < MIN(set1->size, set2->size); i++)
     if (set2->bitmap[i] != 0)
@@ -300,7 +301,7 @@ void xbt_setset_substract(xbt_setset_set_t set1, xbt_setset_set_t set2)
  */
 void xbt_setset_intersect(xbt_setset_set_t set1, xbt_setset_set_t set2)
 {
-  int i;
+  unsigned int i;
 
   for (i = 0; i < MIN(set1->size, set2->size); i++)
     if (set1->bitmap[i] && set2->bitmap[i])
@@ -313,7 +314,7 @@ void xbt_setset_intersect(xbt_setset_set_t set1, xbt_setset_set_t set2)
 void xbt_setset_cursor_first(xbt_setset_set_t set,
                              xbt_setset_cursor_t * cursor)
 {
-  int i;
+  unsigned int i;
   (*cursor) = xbt_new0(s_xbt_setset_cursor_t, 1);
   (*cursor)->set = set;
 
index 128db63..3099ed1 100644 (file)
@@ -4,6 +4,7 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#include "xbt/base.h"
 #include "xbt/dict.h"
 #include "xbt/dynar.h"
 #include "xbt/setset.h"
@@ -44,16 +45,16 @@ typedef struct s_xbt_setset_cursor {
 
 /* Some internal functions */
 
-int bitcount(int);
+XBT_PRIVATE int bitcount(int);
 
 /* Get the object associated to a given index */
-void *_xbt_setset_idx_to_obj(xbt_setset_t setset, unsigned long idx);
+XBT_PRIVATE void *_xbt_setset_idx_to_obj(xbt_setset_t setset, unsigned long idx);
 
 /* Check if the nth bit of an integer is set or not*/
-unsigned int _is_bit_set(unsigned int bit, unsigned int integer);
+XBT_PRIVATE unsigned int _is_bit_set(unsigned int bit, unsigned int integer);
 
 /* Set the nth bit of an array of integers */
-void _set_bit(unsigned int bit, unsigned int *bitmap);
+XBT_PRIVATE void _set_bit(unsigned int bit, unsigned int *bitmap);
 
 /* Unset the nth bit of an array of integers */
-void _unset_bit(unsigned int bit, unsigned int *bitmap);
+XBT_PRIVATE void _unset_bit(unsigned int bit, unsigned int *bitmap);
index a73d120..80dd2e5 100644 (file)
@@ -65,12 +65,12 @@ int makecontext(ucontext_t * ucp, void (*func) (), int argc, ...)
   }
   
       /* Set the instruction and the stack pointer */
-  #if defined(_I_X86_) || defined(__i386) || defined(__i386__)
+  #if defined(_I_X86_) || defined(__i386) || defined(__i386__) || defined(_M_IX86)
   ucp->uc_mcontext.Eip = (DWORD) func;
   ucp->uc_mcontext.Esp = (DWORD) sp - sizeof(void*);
   #elif defined(_IA64_) || defined(__ia64) || defined(__ia64__)
   #  error "_IA64_"
-  #elif defined _AMD64_ || defined(__x86_64) || defined(__x86_64__)
+  #elif defined _AMD64_ || defined(__x86_64) || defined(__x86_64__) || defined(_M_X64)
   ucp->uc_mcontext.Rip = (DWORD64) func;
   ucp->uc_mcontext.Rsp = (DWORD64) sp - sizeof(void*);
   #else
index d06d9b9..5342776 100644 (file)
@@ -105,7 +105,7 @@ static void append2_file(xbt_log_appender_t this_, char *str) {
    fputs(str, d->file);
    if(d->count<0){
           fputs(APPEND2_END_TOKEN,d->file);
-          fseek(d->file,-strlen(APPEND2_END_TOKEN),SEEK_CUR);
+          fseek(d->file,-((signed long)strlen(APPEND2_END_TOKEN)),SEEK_CUR);
    }
 }
 
index d07d4a3..e1a234f 100644 (file)
@@ -6,6 +6,8 @@
 /* This program is free software; you can redistribute it and/or modify it
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
+#define XBT_LOG_LOCALLY_DEFINE_XBT_CHANNEL /* MSVC don't want it to be declared extern in headers and local here */
+
 #include "xbt/misc.h"
 #include "simgrid_config.h"     /* _XBT_WIN32 */
 #include "internal_config.h"    /* MMALLOC_WANT_OVERRIDE_LEGACY */
@@ -26,7 +28,6 @@
 #include <signal.h>
 #endif
 
-XBT_LOG_NEW_CATEGORY(xbt, "All XBT categories (simgrid toolbox)");
 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(module, xbt, "module handling");
 
 XBT_LOG_NEW_CATEGORY(smpi, "All SMPI categories"); /* lives here even if that's a bit odd to solve linking issues: this is used in xbt_log_file_appender to detect whether SMPI is used (and thus whether we should unbench the writing to disk) */
@@ -123,6 +124,7 @@ static void xbt_preinit(void) {
 static void xbt_postexit(void)
 {
   if(!_sg_do_clean_atexit) return;
+  xbt_initialized--;
   xbt_backtrace_postexit();
   xbt_fifo_postexit();
   xbt_dict_postexit();
index 333d5cd..9cb965c 100644 (file)
@@ -185,7 +185,7 @@ xbt_matrix_t xbt_matrix_double_new_seq(int lines, int rows)
 /** \brief Checks whether the matrix contains the sequence of numbers */
 int xbt_matrix_double_is_seq(xbt_matrix_t mat)
 {
-  int i;
+  unsigned int i;
 
   for (i = 0; i < mat->lines * mat->rows; i++) {
     double val = xbt_matrix_get_as(mat, i, 0, double);
diff --git a/src/xbt/xbt_os_file.c b/src/xbt/xbt_os_file.c
new file mode 100644 (file)
index 0000000..43c30bb
--- /dev/null
@@ -0,0 +1,94 @@
+/* xbt_os_file.c -- portable interface to file-related functions            */
+
+/* Copyright (c) 2007-2010, 2012-2015. The SimGrid Team.
+ * All rights reserved.                                                     */
+
+/* This program is free software; you can redistribute it and/or modify it
+ * under the terms of the license (GNU LGPL) which comes with this package. */
+
+#include "xbt/sysdep.h"
+#include "xbt/file.h"    /* this module */
+#include "xbt/log.h"
+#include "portable.h"
+
+#ifndef _MSC_VER
+#include "libgen.h" /* POSIX dirname */
+#endif
+
+/** @brief Get a single line from the stream (reimplementation of the GNU getline)
+ *
+ * This is a reimplementation of the GNU getline function, so that our code don't depends on the GNU libc.
+ *
+ * xbt_getline() reads an entire line from stream, storing the address of the
+ * buffer containing the text into *buf.  The buffer is null-terminated and
+ * includes the newline character, if one was found.
+ *
+ * If *buf is NULL, then xbt_getline() will allocate a buffer for storing the
+ * line, which should be freed by the user program.
+ *
+ * Alternatively, before calling xbt_getline(), *buf can contain a pointer to a
+ * malloc()-allocated buffer *n bytes in size.  If the buffer is not large
+ * enough to hold the line, xbt_getline() resizes it with realloc(), updating
+ * *buf and *n as necessary.
+ *
+ * In either case, on a successful call, *buf and *n will be updated to reflect
+ * the buffer address and allocated size respectively.
+ */
+ssize_t xbt_getline(char **buf, size_t *n, FILE *stream)
+{
+  ssize_t i;
+  int ch;
+
+  ch = getc(stream);
+  if (ferror(stream) || feof(stream))
+    return -1;
+
+  if (!*buf) {
+    *n = 512;
+    *buf = xbt_malloc(*n);
+  }
+
+  i = 0;
+  do {
+    if (i == *n)
+      *buf = xbt_realloc(*buf, *n += 512);
+    (*buf)[i++] = ch;
+  } while (ch != '\n' && (ch = getc(stream)) != EOF);
+
+  if (i == *n)
+    *buf = xbt_realloc(*buf, *n += 1);
+  (*buf)[i] = '\0';
+
+  return i;
+}
+
+/** @brief Returns the directory component of a path (reimplementation of POSIX dirname)
+ *
+ * The argument is never modified, and the returned value must be freed after use.
+ */
+char *xbt_dirname(const char *path) {
+#if _MSC_VER
+         char drive[_MAX_DRIVE];
+         char dir[_MAX_DIR];
+         errno_t err;
+         err = _splitpath_s(path, drive, _MAX_DRIVE, dir, _MAX_DIR, NULL,0, NULL,0);
+         return bprintf("%s%s",drive,dir);
+#else
+         return dirname(xbt_strdup(path));
+#endif
+}
+/** @brief Returns the file component of a path (reimplementation of POSIX basename)
+ *
+ * The argument is never modified, and the returned value must be freed after use.
+ */
+char *xbt_basename(const char *path) {
+#if _MSC_VER
+         char file[1024];
+         char ext[1024];
+         errno_t err;
+         err = _splitpath_s(path, NULL,0, NULL,0, file,1024, ext,1024);
+         return bprintf("%s.%s",file,ext);
+#else
+         return basename(xbt_strdup(path));
+#endif
+}
index d7545b4..91db34b 100644 (file)
@@ -111,7 +111,7 @@ void xbt_os_thread_mod_preinit(void)
 
   if ((errcode = pthread_setspecific(xbt_self_thread_key, main_thread)))
     THROWF(system_error, errcode,
-           "pthread_setspecific failed for xbt_self_thread_key");
+           "Impossible to set the SimGrid identity descriptor to the main thread (pthread_setspecific failed)");
   
   __xbt_running_ctx_fetch = _os_thread_get_running_ctx;
   __xbt_ex_terminate = _os_thread_ex_terminate;
@@ -729,6 +729,16 @@ static unsigned long xbt_self_thread_key;
 void xbt_os_thread_mod_preinit(void)
 {
   xbt_self_thread_key = TlsAlloc();
+
+  xbt_os_thread_t main_thread = xbt_new0(s_xbt_os_thread_t, 1);
+  main_thread->name = (char *) "main";
+  main_thread->start_routine = NULL;
+  main_thread->param = NULL;
+
+  if (!TlsSetValue(xbt_self_thread_key, main_thread))
+    THROWF(system_error, (int)GetLastError(),
+           "Impossible to set the SimGrid identity descriptor to the main thread (TlsSetValue() failed)");
+
 }
 
 void xbt_os_thread_mod_postexit(void)
index 1027ecf..8187da1 100644 (file)
@@ -371,7 +371,6 @@ void xbt_os_threadtimer_start(xbt_os_timer_t timer)
   timer->elapse.tv_usec = 0;
   gettimeofday(&(timer->start), NULL);
 #elif defined(_XBT_WIN32)
-  struct timeval tv;
 #  if defined(WIN32_WCE) || (_WIN32_WINNT < 0x0400)
   THROW_UNIMPLEMENTED;
 #  else
index 5012744..2802f52 100644 (file)
@@ -5,11 +5,13 @@
  * under the terms of the license (GNU LGPL) which comes with this package. */
 
 #include "internal_config.h"
-#include <errno.h>
 #include "xbt/sysdep.h"
 #include "xbt/log.h"
 #include "xbt/str.h"
+#include "xbt/file.h"
 #include "xbt/replay.h"
+
+#include <errno.h>
 #include <ctype.h>
 #include <wchar.h>
 
index 149fb39..c8d83be 100644 (file)
@@ -22,7 +22,7 @@
 
 #ifndef CONTEXT_THREADS
 #ifndef WIN32
-#ifdef HAVE_PTHREAD_H
+#ifdef HAVE_PTHREAD
 /* xbt_threads is loaded in libsimgrid when they are used to implement the xbt_context.
  * The decision (and the loading) is made in xbt/context.c.
  */
index 6290cd9..e2973ca 100644 (file)
@@ -58,7 +58,7 @@ void xbt_sha_reset(xbt_sha_t sha)
 /* @brief Add some more data to the buffer */
 void xbt_sha_feed(xbt_sha_t sha, const unsigned char *data, size_t len)
 {
-  int i;
+  unsigned int i;
 
   for (i = 0; i < len; i++) {
     sha->buf[sha->blen / 4] <<= 8;
index eedfa87..5943a11 100644 (file)
@@ -520,53 +520,6 @@ char *xbt_str_join_array(const char *const *strs, const char *sep)
   return res;
 }
 
-/** @brief Get a single line from the stream (reimplementation of the GNU getline)
- *
- * This is a reimplementation of the GNU getline function, so that our code don't depends on the GNU libc.
- *
- * xbt_getline() reads an entire line from stream, storing the address of the
- * buffer containing the text into *buf.  The buffer is null-terminated and
- * includes the newline character, if one was found.
- *
- * If *buf is NULL, then xbt_getline() will allocate a buffer for storing the
- * line, which should be freed by the user program.
- *
- * Alternatively, before calling xbt_getline(), *buf can contain a pointer to a
- * malloc()-allocated buffer *n bytes in size.  If the buffer is not large
- * enough to hold the line, xbt_getline() resizes it with realloc(), updating
- * *buf and *n as necessary.
- *
- * In either case, on a successful call, *buf and *n will be updated to reflect
- * the buffer address and allocated size respectively.
- */
-ssize_t xbt_getline(char **buf, size_t *n, FILE *stream)
-{
-  ssize_t i;
-  int ch;
-
-  ch = getc(stream);
-  if (ferror(stream) || feof(stream))
-    return -1;
-
-  if (!*buf) {
-    *n = 512;
-    *buf = xbt_malloc(*n);
-  }
-
-  i = 0;
-  do {
-    if (i == *n)
-      *buf = xbt_realloc(*buf, *n += 512);
-    (*buf)[i++] = ch;
-  } while (ch != '\n' && (ch = getc(stream)) != EOF);
-
-  if (i == *n)
-    *buf = xbt_realloc(*buf, *n += 1);
-  (*buf)[i] = '\0';
-
-  return i;
-}
-
 /*
  * Diff related functions
  *
@@ -908,7 +861,7 @@ char *xbt_str_from_file(FILE * file)
  */
 int xbt_str_start_with(const char* str, const char* start)
 {
-  int i;
+  unsigned int i;
   size_t l_str = strlen(str);
   size_t l_start = strlen(start);
 
index 6a8ea1d..4d9dfd7 100644 (file)
@@ -31,6 +31,10 @@ void xbt_os_thread_mod_postexit(void);
 void *mmalloc_preinit(void);
 void mmalloc_postexit(void);
 
+extern int smx_cleaned;
+extern int xbt_initialized;
+
+
 SG_END_DECL()
 
 #endif                          /* XBT_MODINTER_H */
index 3f46bf1..366825d 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
       set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 50284bc..1e0ef76 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 set(xml_files
index df403b7..18c2174 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(example java_sleep_host_off)
 set(sources
   ${CMAKE_CURRENT_SOURCE_DIR}/Main.java
index b6e1d81..8256397 100644 (file)
@@ -1,20 +1,18 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(HAVE_MC)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 endif()
 
-add_executable(mutex_handling mutex_handling.c)
-target_link_libraries(mutex_handling simgrid)
+add_executable(with_mutex_handling mutex_handling.c)
+target_link_libraries(with_mutex_handling simgrid)
 
-add_executable(no_mutex_handling mutex_handling.c)
-target_link_libraries(no_mutex_handling simgrid)
-set_target_properties(no_mutex_handling PROPERTIES COMPILE_FLAGS -DDISABLE_THE_MUTEX=1)
+add_executable(without_mutex_handling mutex_handling.c)
+target_link_libraries(without_mutex_handling simgrid)
+set_target_properties(without_mutex_handling PROPERTIES COMPILE_FLAGS -DDISABLE_THE_MUTEX=1)
 
 set(tesh_files
   ${tesh_files}
-  ${CMAKE_CURRENT_SOURCE_DIR}/mutex_handling.tesh
-  ${CMAKE_CURRENT_SOURCE_DIR}/no_mutex_handling.tesh
+  ${CMAKE_CURRENT_SOURCE_DIR}/with_mutex_handling.tesh
+  ${CMAKE_CURRENT_SOURCE_DIR}/without_mutex_handling.tesh
   PARENT_SCOPE
   )
 set(testsuite_src
index 00e46e9..19d6829 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(HAVE_MC)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
index ee7138c..91693d3 100644 (file)
@@ -17,8 +17,8 @@
 #include "mc/datatypes.h"
 #include "mc/mc_object_info.h"
 #include "mc/mc_private.h"
-#include "mc/mc_process.h"
 
+#include "mc/Process.hpp"
 #include "mc/Type.hpp"
 #include "mc/ObjectInformation.hpp"
 #include "mc/Variable.hpp"
@@ -100,9 +100,9 @@ static simgrid::mc::Variable* test_global_variable(simgrid::mc::Process* process
   return variable;
 }
 
-static simgrid::mc::Type* find_member(simgrid::mc::ObjectInformation* info, const char* name, simgrid::mc::Type* type)
+static simgrid::mc::Member* find_member(simgrid::mc::Type& type, const char* name)
 {
-  for (simgrid::mc::Type& member : type->members)
+  for (simgrid::mc::Member& member : type.members)
     if(member.name == name)
       return &member;
   return nullptr;
@@ -146,8 +146,10 @@ int main(int argc, char** argv)
   i = process->binary_info->types.find(var->type_id);
   xbt_assert(i != process->binary_info->types.end(), "Missing type");
   type = &i->second;
-  assert(find_member(process->binary_info.get(), "first", type)->offset() == 0);
-  assert(find_member(process->binary_info.get(), "second", type)->offset()
+
+  assert(type);
+  assert(find_member(*type, "first")->offset() == 0);
+  assert(find_member(*type, "second")->offset()
       == ((const char*)&test_some_struct.second) - (const char*)&test_some_struct);
 
   unw_context_t context;
index 838ee57..9801f45 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(HAVE_MC)
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
index 32798ad..98ce207 100644 (file)
 #include <assert.h>
 #include <stdlib.h>
 
-#include "mc/mc_process.h"
 #include "mc/mc_private.h"
 #include "mc/mc_object_info.h"
 
+#include "mc/Process.hpp"
 #include "mc/Type.hpp"
 #include "mc/ObjectInformation.hpp"
 #include "mc/Variable.hpp"
diff --git a/teshsuite/mc/mutex_handling.tesh b/teshsuite/mc/mutex_handling.tesh
deleted file mode 100644 (file)
index 4839f3f..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-#!/usr/bin/env tesh
-! expect return 1
-! output ignore
-$ ${bindir:=.}/../../bin/simgrid-mc ${bindir:=.}/mutex_handling --cfg=model-check:1 ../../examples/platforms/platform.xml mutex_handling.xml
diff --git a/teshsuite/mc/no_mutex_handling.tesh b/teshsuite/mc/no_mutex_handling.tesh
deleted file mode 100644 (file)
index 58f31e8..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-#!/usr/bin/env tesh
-! expect return 1
-! output ignore
-$ ${bindir:=.}/../../bin/simgrid-mc ${bindir:=.}/no_mutex_handling --cfg=model-check:1 ../../examples/platforms/platform.xml mutex_handling.xml
index 806d651..e4e986d 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 add_executable(random_bug random_bug.c)
 target_link_libraries(random_bug simgrid)
index c418e24..062c422 100644 (file)
@@ -1,6 +1,6 @@
 #!/usr/bin/env tesh
 ! expect return 1
-$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/random_bug ${srcdir:=.}/../../../examples/platforms/small_platform.xml ${srcdir:=.}/random_bug.xml "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --log=xbt_cfg.thresh:warning --cfg=model-check:1 --cfg=model-check/record:1
+$ ${bindir:=.}/../../../bin/simgrid-mc ${bindir:=.}/random_bug ${srcdir:=.}/../../../examples/platforms/small_platform.xml ${srcdir:=.}/random_bug.xml "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n" --log=xbt_cfg.thresh:warning --cfg=model-check/record:1
 > [  0.000000] (0:@) Check a safety property
 > [  0.000000] (0:@) **************************
 > [  0.000000] (0:@) *** PROPERTY NOT VALID ***
diff --git a/teshsuite/mc/with_mutex_handling.tesh b/teshsuite/mc/with_mutex_handling.tesh
new file mode 100644 (file)
index 0000000..0df840c
--- /dev/null
@@ -0,0 +1,4 @@
+#!/usr/bin/env tesh
+! expect return 1
+! output ignore
+$ ${bindir:=.}/../../bin/simgrid-mc ${bindir:=.}/with_mutex_handling ../../examples/platforms/platform.xml mutex_handling.xml
diff --git a/teshsuite/mc/without_mutex_handling.tesh b/teshsuite/mc/without_mutex_handling.tesh
new file mode 100644 (file)
index 0000000..f950a22
--- /dev/null
@@ -0,0 +1,4 @@
+#!/usr/bin/env tesh
+! expect return 1
+! output ignore
+$ ${bindir:=.}/../../bin/simgrid-mc ${bindir:=.}/without_mutex_handling ../../examples/platforms/platform.xml mutex_handling.xml
index 8a8ce53..0b5b777 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 ### Add definitions for compile
index 39bfe70..7f9b57b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(get_sender get_sender.c)
index a91b238..68bd184 100644 (file)
@@ -11,7 +11,7 @@
 XBT_LOG_NEW_DEFAULT_CATEGORY(test, "Messages specific to this example");
 
 
-static int send(int argc, char *argv[])
+static int sender_fun(int argc, char *argv[])
 {
   XBT_INFO("Sending");
   MSG_task_send(MSG_task_create("Blah", 0.0, 0.0, NULL), MSG_host_get_name(MSG_host_self()));
@@ -20,7 +20,7 @@ static int send(int argc, char *argv[])
   return 0;
 }
 
-static int receive(int argc, char *argv[])
+static int receiver_fun(int argc, char *argv[])
 {
   XBT_INFO("Receiving");
   msg_task_t task = NULL;
@@ -40,8 +40,8 @@ int main(int argc, char *argv[])
   MSG_init(&argc, argv);
 
   /*   Application deployment */
-  MSG_function_register("send", &send);
-  MSG_function_register("receive", &receive);
+  MSG_function_register("send", &sender_fun);
+  MSG_function_register("receive", &receiver_fun);
 
   MSG_create_environment(argv[1]);
   MSG_launch_application(argv[2]);
index 5acd204..e6c78e1 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 foreach(x host_on_off host_on_off_wait host_on_off_recv)
index 2c5727e..9d6544d 100644 (file)
@@ -75,7 +75,7 @@ int master(int argc, char *argv[])
 int slave(int argc, char *argv[])
 {
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   int id = -1;
   char mailbox[80];
 
index cc286af..bd6a7bd 100644 (file)
@@ -45,6 +45,7 @@ int master(int argc, char *argv[])
 
     if (comm) {
       MSG_comm_wait(comm, -1);
+      MSG_comm_destroy(comm);
     }
     XBT_INFO("Master has finished");
   }
index 6109947..a2ab6a5 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(host_on_off_processes host_on_off_processes.c)
index b2eb287..7fd2ced 100644 (file)
@@ -254,6 +254,7 @@ int main(int argc, char *argv[])
      sscanf(xbt_dynar_get_as(s_tests, iter, char *), "%d", &tmp_test);
      xbt_dynar_set_as(tests, iter, int, tmp_test);
   }
+  xbt_dynar_free(&s_tests);
 
   platform_file = argv[1];
   application_file = argv[2];
index a19568a..f906c05 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(pid pid.c)
index 483ca0b..8542e30 100644 (file)
@@ -13,7 +13,7 @@ const char* mailbox = "mailbox";
 #define task_comp_size 1000
 #define task_comm_size 100000
 
-static int onexit(smx_process_exit_status_t status, int *pid){
+static int my_onexit(smx_process_exit_status_t status, int *pid){
   XBT_INFO("Process \"%d\" killed.", *pid);
   return 0;
 }
@@ -21,7 +21,7 @@ static int onexit(smx_process_exit_status_t status, int *pid){
 static int sendpid(int argc, char *argv[])
 {
   int pid = MSG_process_self_PID();
-  MSG_process_on_exit((int_f_pvoid_pvoid_t)onexit, &pid);
+  MSG_process_on_exit((int_f_pvoid_pvoid_t)my_onexit, &pid);
   msg_task_t task = MSG_task_create("pid", task_comp_size, task_comm_size, &pid);
   XBT_INFO("Sending pid of \"%d\".", pid);
   MSG_task_send(task, mailbox);
@@ -32,7 +32,7 @@ static int sendpid(int argc, char *argv[])
 
 static int killall(int argc, char *argv[]){
   msg_task_t task = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   int i;
   for (i=0; i<3;i++) {
     res = MSG_task_receive(&(task), mailbox);
index 05fb130..00d7576 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(process process.c)
index a7de14e..cdd4d36 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(process_join ${CMAKE_HOME_DIRECTORY}/teshsuite/msg/process_join/process_join.c)
index 223bd66..89e4b2e 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(storage_basic storage_basic.c)
index 83046c1..63f322d 100644 (file)
@@ -168,7 +168,7 @@ int client(int argc, char *argv[])
 int server(int argc, char *argv[])
 {
   msg_task_t to_execute = NULL;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
 
   storage_info(MSG_host_self());
 
index 97968dc..6d709e6 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(task_destroy_cancel task_destroy_cancel.c)
index 048e817..cc9ea1c 100644 (file)
@@ -94,7 +94,7 @@ static int worker_main(int argc, char *argv[])
 int slave(int argc, char *argv[])
 {
   msg_task_t task;
-  _XBT_GNUC_UNUSED int res;
+  XBT_ATTRIB_UNUSED int res;
   int id = -1;
   char mailbox[80];
   double start, end;
index 761bddc..089d9ee 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(test_trace_integration test_trace_integration.c)
index a866b6d..67e641c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(availability_test availability_test.c)
index 9e308cb..b23c3b0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(basic0 basic0.c)
index 98bff3c..ef0660c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(incomplete incomplete.c)
index a89ec1c..801abab 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(test_reinit_costs test_reinit_costs.c)
index e25af1c..a303490 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(test_intra_all2all test_intra_all2all.c)
index d511b08..638c6c0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(test_latency1 test_latency1.c)
index a126fcf..45248fa 100644 (file)
@@ -1,9 +1,8 @@
 
 p Reinitialization test
-! output sort
 
+! expect signal SIGABRT
 $ simdag/network/test_reinit_costs ${srcdir:=.}/simdag/network/platform_2p_1sl.xml --cfg=path:${srcdir} --log=sd_kernel.thres=warning "--log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n"
 > [  0.000000] (0:@) Switching to the L07 model to handle parallel tasks.
-> 0
-> [  0.000000] (0:@) Switching to the L07 model to handle parallel tasks.
-> 1.5
+> [  0.000000] (0:@) This function is not working since the C++ links and others. Please report the problem if you really need that function.
+
index 1d57c19..2d6d0cd 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(test_comp_only_seq test_comp_only_seq.c)
index d65ba9f..c54438b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(basic_parsing_test basic_parsing_test.c)
index 4c78962..abea074 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(check_defaults check_defaults.c)
index e039545..b1f00d9 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(stack_overflow stack_overflow.c)
index c988e77..2123cff 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 6ed0ecb..2bab00c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 7544520..f3e6d3f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 69511aa..85f36d0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index c4ad546..3d457cf 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 5c96bad..a76bcbf 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 72fd58f..a3fbb2e 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 2764358..286a9a1 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 45bd3fa..c25ecea 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 3bfd8da..7d1b3b2 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 99fddbf..c72e295 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 927e849..49300b3 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
diff --git a/teshsuite/smpi/isp/umpire/.gitignore b/teshsuite/smpi/isp/umpire/.gitignore
new file mode 100644 (file)
index 0000000..06fb7b0
--- /dev/null
@@ -0,0 +1 @@
+*.tesh
index ac4e2da..e20f7bd 100644 (file)
-cmake_minimum_required(VERSION 2.6)
+# See http://formalverification.cs.utah.edu/ISP_Tests/
 
-set(umpire_src
+set(umpire_tests_passing
+  change-send-buffer
+  comm-dup-no-error
+  comm-dup-no-free
+  comm-dup-no-free2
+  comm-simple
+  comm-split-no-free
+  comm-translate-ranks
+  hello
+  no-error
+  no-error2
+  no-error3
+  no-error3-any_src
+  no-error-any_src
+  no-error-interleaved-isend
+  no-error-test
+  no-error-testall
+  no-error-testany
+  no-error-vector-isend
+  no-error-wait
+  no-error-waitany-any_src2
+  no-error-waitany-any_src3
+  no-error-waitany
+  no-error-wait-any_src
+  no-error-wait-any_src2
+  no-error-wait-any_src3
+  no-error-wait-any_src4
+  no-error-waitany-any_src
+  partial-recv
+  sendrecv-deadlock
+  send-recv-ok
+  irecv-isend-ok
+  irecv-isend-ok2
+  lost-request-waitall
+ ) # Passing (no deadlock) tests
+
+# These are supposed to deadlock but ISP does not find deadlock
+# and we don't either. What should be test here?
+set(umpire_tests_missed_deadlock
+  any_src-deadlock
+  any_src-can-deadlock
+  any_src-can-deadlock2
+  any_src-can-deadlock3
+  )
+
+set(umpire_tests_deadlock
+  any_src-can-deadlock10
+  any_src-can-deadlock10_mod
+  any_src-can-deadlock11
+  any_src-can-deadlock4
+  any_src-can-deadlock4_mod
+  any_src-can-deadlock5
+  any_src-can-deadlock5_mod
+  any_src-can-deadlock6
+  any_src-can-deadlock6_mod
+  any_src-can-deadlock7
+  any_src-can-deadlock8
+  any_src-can-deadlock9
+  any_src-waitall-deadlock
+  any_src-waitall-deadlock2
+  any_src-waitall-deadlock3
+  any_src-waitany-deadlock2
+  any_src-waitany-deadlock
+  any_src-wait-deadlock
+  any_src-wait-deadlock2
+  basic-deadlock
+  basic-deadlock-comm_create
+  basic-deadlock-comm_dup
+  basic-deadlock-comm_split
+  bcast-deadlock
+  collective-misorder
+  collective-misorder2
+  collective-misorder-allreduce
+  comm-bcast-deadlock
+  comm-deadlock
+  complex-deadlock
+  dropped-req
+  finalize-deadlock
+  irecv-deadlock
+  waitall-deadlock
+  waitany-deadlock
+  wait-deadlock
+ ) # failing (deadlocking) tests
+set(umpire_tests_problematic
+  deadlock-config # No deadlock detected by ISP unless MPI_Send blocking activated
+
+ ) # problematic tests
+ # These files are not listed on http://formalverification.cs.utah.edu/ISP_Tests/
+set(umpire_src_other
   abort1.c
   abort2.c
   abort3.c
   abort.c
-  any_src-can-deadlock10.c
-  any_src-can-deadlock10_mod.c
-  any_src-can-deadlock11.c
-  any_src-can-deadlock2.c
-  any_src-can-deadlock3.c
-  any_src-can-deadlock4.c
-  any_src-can-deadlock4_mod.c
-  any_src-can-deadlock5.c
-  any_src-can-deadlock5_mod.c
-  any_src-can-deadlock6.c
-  any_src-can-deadlock6_mod.c
-  any_src-can-deadlock7.c
-  any_src-can-deadlock8.c
-  any_src-can-deadlock9.c
-  any_src-can-deadlock.c
-  any_src-deadlock.c
-  any_src-waitall-deadlock2.c
-  any_src-waitall-deadlock3.c
-  any_src-waitall-deadlock.c
-  any_src-waitany-deadlock2.c
-  any_src-waitany-deadlock.c
-  any_src-wait-deadlock2.c
-  any_src-wait-deadlock.c
-  basic-deadlock.c
   basic-deadlock-cart_create.c
   basic-deadlock-cart_sub.c
-  basic-deadlock-comm_create.c
-  basic-deadlock-comm_dup.c
-  basic-deadlock-comm_split.c
   basic-deadlock-graph_create.c
   basic-deadlock-intercomm_create.c
   basic-deadlock-intercomm_merge.c
-  bcast-deadlock.c
-  change-send-buffer.c
   change-send-buffer-exhaustive.c
   change-send-buffer-type-exhaustive.c
   collective-exhaustive-byte-int-mismatch.c
   collective-exhaustive-no-error.c
-  collective-misorder2.c
-  collective-misorder-allreduce.c
   collective-misorder.c
-  comm-bcast-deadlock.c
-  comm-deadlock.c
-  comm-dup-no-error.c
-  comm-dup-no-free2.c
-  comm-dup-no-free.c
-  comm-simple.c
-  comm-split-no-free.c
-  comm-translate-ranks.c
-  complex-deadlock.c
+  collective-misorder2.c
+
   deadlock-config_blocking.c
-  deadlock-config.c
-  dropped-req.c
   errhandler-no-error.c
   errhandler-no-free.c
-  finalize-deadlock.c
   group-no-error2.c
   group-no-error3.c
   group-no-error.c
@@ -69,29 +118,19 @@ set(umpire_src
   group-no-free3.c
   group-no-free.c
   group-no-free-exhaustive.c
-  hello.c
   intercomm_create-deadlock2.c
   intercomm_create-deadlock3.c
   intercomm_create-deadlock4.c
   intercomm_create-deadlock.c
   intercomm_create-no-error.c
   intercomm_merge-deadlock.c
-  irecv-deadlock.c
-  irecv-isend-ok2.c
-  irecv-isend-ok.c
   lost-request2.c
   lost-request3.c
-  lost-request.c
-  lost-request-waitall.c
-  no-error2.c
-  no-error3-any_src.c
-  no-error3.c
+  lost-request.c  
   no-error4-any_src.c
   no-error4.c
-  no-error-any_src.c
-  no-error.c
   no-error-derived-comms.c
-  no-error-interleaved-isend.c
+    
   no-error-persistent-all-completions.c
   no-error-persistent.c
   no-error-persistent-test.c
@@ -100,28 +139,16 @@ set(umpire_src
   no-error-probe-any_src.c
   no-error-probe-any_tag.c
   no-error-probe.c
-  no-error-testall.c
-  no-error-testany.c
-  no-error-test.c
-  no-error-vector-isend.c
-  # no-error-wait2.c # Does not compile.
+  
+  no-error-wait2.c # Does not compile.
   no-error-waitall-any_src2.c
   no-error-waitall-any_src3.c
   no-error-waitall-any_src.c
   no-error-waitall.c
   no-error-waitany2.c
-  no-error-waitany-any_src2.c
-  no-error-waitany-any_src3.c
-  no-error-waitany-any_src.c
-  no-error-waitany.c
-  no-error-wait-any_src2.c
-  no-error-wait-any_src3.c
-  no-error-wait-any_src4.c
-  no-error-wait-any_src.c
-  no-error-wait.c
+  
   op-no-error.c
   op-no-free.c
-  partial-recv.c
   partial-recv-exhaustive.c
   partial-recv-persistent2.c
   partial-recv-persistent3.c
@@ -136,8 +163,6 @@ set(umpire_src
   probe-deadlock.c
   pt2pt-byte-int-mismatch.c
   remote_group-no-error.c
-  sendrecv-deadlock.c
-  send-recv-ok.c
   type-commit-twice.c
   type-no-error.c
   type-no-error-exhaustive.c
@@ -146,67 +171,65 @@ set(umpire_src
   type-no-free3.c
   type-no-free.c
   type-no-free-exhaustive.c
-  waitall-deadlock.c
-  waitany-deadlock.c
-  wait-deadlock.c
   )
 
-set(sources "")
-FOREACH(s ${umpire_src})
-  set(sources ${sources} ${CMAKE_CURRENT_SOURCE_DIR}/${s})
-ENDFOREACH()
-
-set(umpire_tesh "")
-foreach(tesh
-    any_src-can-deadlock10
-    any_src-can-deadlock4
-    any_src-can-deadlock5
-    any_src-can-deadlock6
-    any_src-waitall-deadlock2
-    any_src-waitall-deadlock3
-    any_src-waitany-deadlock2
-    any_src-waitany-deadlock
-    any_src-wait-deadlock
-    basic-deadlock-comm_create
-    basic-deadlock-comm_dup
-    basic-deadlock-comm_split
-    basic-deadlock
-    bcast-deadlock
-    collective-misorder-allreduce
-    collective-misorder
-    complex-deadlock
-    deadlock-config
-    finalize-deadlock
-    irecv-deadlock
-    no-error2
-    no-error3-any_src
-    no-error3
-    no-error
-    )
-  set(umpire_tesh ${umpire_tesh} teshsuite/smpi/isp/umpire/${tesh}.tesh)
-ENDFOREACH()
-
-set(examples_src ${examples_src} ${sources} PARENT_SCOPE)
-set(txt_files ${txt_files} ${CMAKE_CURRENT_SOURCE_DIR}/README PARENT_SCOPE)
-set(EXTRA_DIST ${EXTRA_DIST} ${CMAKE_CURRENT_SOURCE_DIR}/no-error-wait2.c PARENT_SCOPE)
-set(tesh_files ${tesh_files} ${umpire_tesh} PARENT_SCOPE)
+# Add these files to the archive
+#################
+
+set(sources "${CMAKE_CURRENT_SOURCE_DIR}/README")
+foreach(file ${umpire_src_other})
+  set(sources ${sources} ${CMAKE_CURRENT_SOURCE_DIR}/${file})
+endforeach()
+
+foreach(file ${umpire_tests_passing} ${umpire_tests_deadlock} ${umpire_tests_missed_deadlock} ${umpire_tests_problematic}  ) 
+  set(sources ${sources} ${CMAKE_CURRENT_SOURCE_DIR}/${file}.c)
+endforeach()
+set(txt_files ${txt_files} ${sources} PARENT_SCOPE)
+
+# Build the tests
+#################
 
 if(enable_smpi AND enable_smpi_ISP_testsuite)
-  if(WIN32)
-    set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
-  else()
-    set(CMAKE_C_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpicc")
-    set(CMAKE_Fortran_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpiff")
-  endif()
+  set(CMAKE_C_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpicc")
+  set(CMAKE_Fortran_COMPILER "${CMAKE_BINARY_DIR}/smpi_script/bin/smpiff")
 
   set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
   include_directories(BEFORE "${CMAKE_HOME_DIRECTORY}/include/smpi")
 
-  FOREACH (s ${umpire_src})
-    STRING(REGEX REPLACE "\\.c$" "" exe ${s})
-    add_executable(${exe} ${s})
-    target_link_libraries(${exe} simgrid)
-    set_source_files_properties(${s} PROPERTIES COMPILE_FLAGS "-Wno-error")
-  ENDFOREACH(s)
+  foreach (test ${umpire_tests_passing} ${umpire_tests_deadlock} ${umpire_tests_problematic} )
+    add_executable(${test} ${test}.c)
+    target_link_libraries(${test} simgrid)
+    set_source_files_properties(${test}.c PROPERTIES COMPILE_FLAGS "-Wno-error")
+    set(umpire_tesh ${umpire_tesh} ${test})
+    set(files_to_clean ${files_to_clean} ${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh)
+  endforeach(test)
+  
+  # TODO, what should we do about ${umpire_tests_missed_deadlock}?
+
+  foreach (test ${umpire_tests_passing})
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "! timeout 30")
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "! output display" APPEND)
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "\$ \${bindir:=.}/../../../../bin/smpirun -wrapper \"\${bindir:=.}/../../../../bin/simgrid-mc\" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich \${bindir:=.}/${test} --log=smpi_coll.thresh:error" APPEND)
+  endforeach()
+
+  foreach (test ${umpire_tests_deadlock} ${umpire_tests_problematic} )
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "! timeout 30"     )
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "! expect return 3" APPEND)
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "! output display"  APPEND)
+    write_file(${CMAKE_CURRENT_BINARY_DIR}/${test}.tesh "\$ \${bindir:=.}/../../../../bin/smpirun -wrapper \"\${bindir:=.}/../../../../bin/simgrid-mc\" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich \${bindir:=.}/${test} --log=smpi_coll.thresh:error" APPEND)
+  endforeach()
+endif()
+
+# Erase all tesh files on cleanup: they are generated anyway
+set_directory_properties ( PROPERTIES ADDITIONAL_MAKE_CLEAN_FILES "${files_to_clean}" )
+
+if(enable_smpi AND enable_smpi_ISP_testsuite)
+  foreach (tesh ${umpire_tesh})
+    ADD_TESH(mc-umpire-${tesh}
+      --setenv srcdir=${CMAKE_CURRENT_SOURCE_DIR}
+      --setenv bindir=${CMAKE_CURRENT_BINARY_DIR}
+      --cd ${CMAKE_CURRENT_SOURCE_DIR}
+      ${CMAKE_CURRENT_BINARY_DIR}/${tesh}.tesh)
+  endforeach()
 endif()
diff --git a/teshsuite/smpi/isp/umpire/any_src-can-deadlock10.tesh b/teshsuite/smpi/isp/umpire/any_src-can-deadlock10.tesh
deleted file mode 100644 (file)
index ac9ca92..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml -np 3 --log=xbt_cfg.thresh:warning --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-can-deadlock10 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 26
-> [0.000000] [mc_global/INFO] Visited states = 26
-> [0.000000] [mc_global/INFO] Executed transitions = 25
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-can-deadlock4.tesh b/teshsuite/smpi/isp/umpire/any_src-can-deadlock4.tesh
deleted file mode 100644 (file)
index 4a571d4..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml -np 3 --log=xbt_cfg.thresh:warning --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-can-deadlock4 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 26
-> [0.000000] [mc_global/INFO] Visited states = 26
-> [0.000000] [mc_global/INFO] Executed transitions = 25
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-can-deadlock5.tesh b/teshsuite/smpi/isp/umpire/any_src-can-deadlock5.tesh
deleted file mode 100644 (file)
index f2d8447..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --log=xbt_cfg.thresh:warning --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-can-deadlock5 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 26
-> [0.000000] [mc_global/INFO] Visited states = 26
-> [0.000000] [mc_global/INFO] Executed transitions = 25
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-can-deadlock6.tesh b/teshsuite/smpi/isp/umpire/any_src-can-deadlock6.tesh
deleted file mode 100644 (file)
index 80a06f3..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-can-deadlock6 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 26
-> [0.000000] [mc_global/INFO] Visited states = 26
-> [0.000000] [mc_global/INFO] Executed transitions = 25
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-wait-deadlock.tesh b/teshsuite/smpi/isp/umpire/any_src-wait-deadlock.tesh
deleted file mode 100644 (file)
index cb731e1..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-wait-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 23
-> [0.000000] [mc_global/INFO] Visited states = 23
-> [0.000000] [mc_global/INFO] Executed transitions = 22
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-waitall-deadlock2.tesh b/teshsuite/smpi/isp/umpire/any_src-waitall-deadlock2.tesh
deleted file mode 100644 (file)
index 7f842b4..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-waitall-deadlock2 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 26
-> [0.000000] [mc_global/INFO] Visited states = 26
-> [0.000000] [mc_global/INFO] Executed transitions = 25
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-waitall-deadlock3.tesh b/teshsuite/smpi/isp/umpire/any_src-waitall-deadlock3.tesh
deleted file mode 100644 (file)
index 2c76480..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-waitall-deadlock3 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 29
-> [0.000000] [mc_global/INFO] Visited states = 29
-> [0.000000] [mc_global/INFO] Executed transitions = 28
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-waitany-deadlock.tesh b/teshsuite/smpi/isp/umpire/any_src-waitany-deadlock.tesh
deleted file mode 100644 (file)
index 41ce92f..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-waitany-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 24
-> [0.000000] [mc_global/INFO] Visited states = 24
-> [0.000000] [mc_global/INFO] Executed transitions = 23
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/any_src-waitany-deadlock2.tesh b/teshsuite/smpi/isp/umpire/any_src-waitany-deadlock2.tesh
deleted file mode 100644 (file)
index 9fabceb..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/any_src-waitany-deadlock2 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 29
-> [0.000000] [mc_global/INFO] Visited states = 29
-> [0.000000] [mc_global/INFO] Executed transitions = 28
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/basic-deadlock-comm_create.tesh b/teshsuite/smpi/isp/umpire/basic-deadlock-comm_create.tesh
deleted file mode 100644 (file)
index 7b3e99c..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" --log=xbt_cfg.thresh:warning -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/basic-deadlock-comm_create --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 23
-> [0.000000] [mc_global/INFO] Visited states = 23
-> [0.000000] [mc_global/INFO] Executed transitions = 22
-> (1) Got MPI_COMM_NULL
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/basic-deadlock-comm_dup.tesh b/teshsuite/smpi/isp/umpire/basic-deadlock-comm_dup.tesh
deleted file mode 100644 (file)
index fdaa201..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/basic-deadlock-comm_dup --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 23
-> [0.000000] [mc_global/INFO] Visited states = 23
-> [0.000000] [mc_global/INFO] Executed transitions = 22
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/basic-deadlock-comm_split.tesh b/teshsuite/smpi/isp/umpire/basic-deadlock-comm_split.tesh
deleted file mode 100644 (file)
index 627123f..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/basic-deadlock-comm_split --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 35
-> [0.000000] [mc_global/INFO] Visited states = 35
-> [0.000000] [mc_global/INFO] Executed transitions = 34
-> (1) Derived communicator too small (size = 1)
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/basic-deadlock.tesh b/teshsuite/smpi/isp/umpire/basic-deadlock.tesh
deleted file mode 100644 (file)
index 0135502..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/basic-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 23
-> [0.000000] [mc_global/INFO] Visited states = 23
-> [0.000000] [mc_global/INFO] Executed transitions = 22
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/bcast-deadlock.tesh b/teshsuite/smpi/isp/umpire/bcast-deadlock.tesh
deleted file mode 100644 (file)
index 69e59f0..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/bcast-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 4
-> [0.000000] [mc_global/INFO] Visited states = 4
-> [0.000000] [mc_global/INFO] Executed transitions = 3
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/collective-misorder-allreduce.tesh b/teshsuite/smpi/isp/umpire/collective-misorder-allreduce.tesh
deleted file mode 100644 (file)
index 503a519..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/collective-misorder-allreduce --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 23
-> [0.000000] [mc_global/INFO] Visited states = 23
-> [0.000000] [mc_global/INFO] Executed transitions = 22
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/collective-misorder.tesh b/teshsuite/smpi/isp/umpire/collective-misorder.tesh
deleted file mode 100644 (file)
index e87bc38..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/collective-misorder --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 45
-> [0.000000] [mc_global/INFO] Visited states = 45
-> [0.000000] [mc_global/INFO] Executed transitions = 44
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/complex-deadlock.tesh b/teshsuite/smpi/isp/umpire/complex-deadlock.tesh
deleted file mode 100644 (file)
index 676481d..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/complex-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 26
-> [0.000000] [mc_global/INFO] Visited states = 26
-> [0.000000] [mc_global/INFO] Executed transitions = 25
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/deadlock-config.tesh b/teshsuite/smpi/isp/umpire/deadlock-config.tesh
deleted file mode 100644 (file)
index 0abb0f2..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/deadlock-config --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> WARNING: This test depends on the MPI's eager limit. Set it appropriately.
-> Initializing (0 of 3)
-> (0) is alive on Tremblay
-> Initializing (1 of 3)
-> (1) is alive on Jupiter
-> Initializing (2 of 3)
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 4
-> [0.000000] [mc_global/INFO] Visited states = 4
-> [0.000000] [mc_global/INFO] Executed transitions = 3
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/finalize-deadlock.tesh b/teshsuite/smpi/isp/umpire/finalize-deadlock.tesh
deleted file mode 100644 (file)
index 1acaa50..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/finalize-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] Expanded states = 20
-> [0.000000] [mc_global/INFO] Visited states = 20
-> [0.000000] [mc_global/INFO] Executed transitions = 19
-> (1) Finished normally
-> (2) Finished normally
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/irecv-deadlock.tesh b/teshsuite/smpi/isp/umpire/irecv-deadlock.tesh
deleted file mode 100644 (file)
index 2f9fb4c..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-#! ./tesh
-
-! expect return 3
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/irecv-deadlock --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] *** DEAD-LOCK DETECTED ***
-> [0.000000] [mc_global/INFO] **************************
-> [0.000000] [mc_global/INFO] Locked request:
-> [0.000000] [mc_global/INFO] Counter-example execution trace:
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iSend(src=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(3)Fafard (2)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iSend(src=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (1)Tremblay (0)])
-> [0.000000] [mc_global/INFO] [(1)Tremblay (0)] iRecv(dst=(1)Tremblay (0), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(2)Jupiter (1)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iSend(src=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] Wait(comm=(verbose only) [(3)Fafard (2)-> (2)Jupiter (1)])
-> [0.000000] [mc_global/INFO] [(2)Jupiter (1)] iRecv(dst=(2)Jupiter (1), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] Wait(comm=(verbose only) [(1)Tremblay (0)-> (3)Fafard (2)])
-> [0.000000] [mc_global/INFO] [(3)Fafard (2)] iRecv(dst=(3)Fafard (2), buff=(verbose only), size=(verbose only))
-> [0.000000] [mc_global/INFO] Expanded states = 22
-> [0.000000] [mc_global/INFO] Visited states = 22
-> [0.000000] [mc_global/INFO] Executed transitions = 21
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/no-error.tesh b/teshsuite/smpi/isp/umpire/no-error.tesh
deleted file mode 100644 (file)
index f180198..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-#! ./tesh
-
-! timeout 5
-! expect return 0
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/no-error --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] Expanded states = 19
-> [0.000000] [mc_global/INFO] Visited states = 46
-> [0.000000] [mc_global/INFO] Executed transitions = 42
-> (2) Finished normally
-> (0) Finished normally
-> (1) Finished normally
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/no-error2.tesh b/teshsuite/smpi/isp/umpire/no-error2.tesh
deleted file mode 100644 (file)
index dcfd5d4..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#! ./tesh
-
-! timeout 5
-! expect return 0
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/no-error2 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] Expanded states = 87
-> [0.000000] [mc_global/INFO] Visited states = 343
-> [0.000000] [mc_global/INFO] Executed transitions = 331
-> (0) Finished normally
-> (1) Finished normally
-> (2) Finished normally
-> (0) Finished normally
-> (0) Finished normally
-> (1) Finished normally
-> (2) Finished normally
-> (0) Finished normally
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/no-error3-any_src.tesh b/teshsuite/smpi/isp/umpire/no-error3-any_src.tesh
deleted file mode 100644 (file)
index 07e0b79..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#! ./tesh
-
-! timeout 5
-! expect return 0
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/no-error3-any_src --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] Expanded states = 80
-> [0.000000] [mc_global/INFO] Visited states = 328
-> [0.000000] [mc_global/INFO] Executed transitions = 315
-> (0) Finished normally
-> (1) Finished normally
-> (2) Finished normally
-> (0) Finished normally
-> (0) Finished normally
-> (1) Finished normally
-> (2) Finished normally
-> (0) Finished normally
-> Aborted
diff --git a/teshsuite/smpi/isp/umpire/no-error3.tesh b/teshsuite/smpi/isp/umpire/no-error3.tesh
deleted file mode 100644 (file)
index b5dd11b..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#! ./tesh
-
-! timeout 5
-! expect return 0
-! output display
-$ ${bindir:=.}/../../../../bin/smpirun -wrapper "${bindir:=.}/../../../../bin/simgrid-mc" -hostfile ../../hostfile -platform ../../../../examples/platforms/small_platform.xml --log=xbt_cfg.thresh:warning -np 3 --cfg=model-check:1 --cfg=smpi/running_power:1e9 --cfg=smpi/coll_selector:mpich ${bindir:=.}/no-error3 --log=smpi_coll.thresh:error
-> [0.000000] [mc_safety/INFO] Check a safety property
-> (0) is alive on Tremblay
-> (1) is alive on Jupiter
-> (2) is alive on Fafard
-> [0.000000] [mc_global/INFO] Expanded states = 80
-> [0.000000] [mc_global/INFO] Visited states = 328
-> [0.000000] [mc_global/INFO] Executed transitions = 315
-> (0) Finished normally
-> (1) Finished normally
-> (2) Finished normally
-> (0) Finished normally
-> (0) Finished normally
-> (1) Finished normally
-> (2) Finished normally
-> (0) Finished normally
-> Aborted
index ff018b3..a25fef7 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index ab26692..0c6ed52 100755 (executable)
@@ -1,4 +1,4 @@
-#! /usr/local/bin/perl
+#! /usr/bin/env perl
 
 $debug   = 1;
 $verbose = 1;
index 08564d8..42ab296 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index ca98ccb..ce971b5 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 7568eec..5a26dcb 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 9e4767b..3a18100 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 2db2d5e..4c9d34c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index b3017ef..ac440db 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 79dc501..0e1d4d7 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 161fc31..5026d9b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index c0912b3..115ddf5 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index af11de1..0491a17 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index c75bfc8..16f995f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index d1e702c..3595f85 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 2e39977..4f2703a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index ab18767..f0bff73 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 95a7b5e..bdefabe 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index a400a1c..05a3d79 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index b538ccc..11e84f2 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 0f0449f..f3aaa77 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 564a213..2c3f619 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index dc43b48..32f074a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index d7295b2..01eafe2 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite AND SMPI_FORTRAN)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 313a147..65b7bc8 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 8fb1632..e7f412c 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 4e8cf0b..64b9266 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 8c810c2..85760a4 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index cd94670..656d79b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 5bdeacf..4bbd73f 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 8d28884..b356be9 100755 (executable)
@@ -1,4 +1,4 @@
-#! /usr/bin/perl
+#! /usr/bin/env perl
 # -*- Mode: perl; -*-
 #
 # This script is the beginnings of a script to run a sequence of test
index 5224a24..84181a0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi AND enable_smpi_MPICH3_testsuite)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 642cf71..6fb21c9 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 4b9bc6c..b32da37 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 0df80e4..bfa8644 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 8ad5a31..d1a19c0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 5a48e12..c45cbc3 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 388a732..44c4480 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 if(enable_smpi)
   if(WIN32)
     set(CMAKE_C_FLAGS "-include ${CMAKE_HOME_DIRECTORY}/include/smpi/smpi_main.h")
index 50284bc..1e0ef76 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 set(xml_files
index aa20eb3..7284c8d 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(lmm_usage ${CMAKE_HOME_DIRECTORY}/teshsuite/surf/lmm_usage/lmm_usage.c)
index c58f9c6..3d7dfab 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(maxmin_bench ${CMAKE_HOME_DIRECTORY}/teshsuite/surf/maxmin_bench/maxmin_bench.c)
index 7f1a309..43a48bd 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(surf_usage ${CMAKE_HOME_DIRECTORY}/teshsuite/surf/surf_usage/surf_usage.c)
index c7ed9b5..bbe4500 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(trace_usage ${CMAKE_HOME_DIRECTORY}/teshsuite/surf/trace_usage/trace_usage.c)
index b2850ad..e9c2066 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(graphxml_usage ${CMAKE_HOME_DIRECTORY}/teshsuite/xbt/graphxml_usage/graphxml_usage.c)
index d80764e..0d11fc0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(heap_bench ${CMAKE_HOME_DIRECTORY}/teshsuite/xbt/heap_bench/heap_bench.c)
index 120c864..4420c95 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(log_large_test log_large_test.c)
index 38f5c84..3a1fe76 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(log_usage ${CMAKE_HOME_DIRECTORY}/teshsuite/xbt/log_usage/log_usage.c)
index 7935111..a364217 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(mallocator mallocator_test.c)
index 729cb04..508321a 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 if(HAVE_MMALLOC)
index 069181a..893d9aa 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(parallel_log_crashtest parallel_log_crashtest.c)
index 1a09636..345884b 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(parmap_bench ${CMAKE_HOME_DIRECTORY}/teshsuite/xbt/parmap_bench/parmap_bench.c)
index 1f8d63d..94d6aeb 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_CURRENT_BINARY_DIR}")
 
 add_executable(parmap_test parmap_test.c)
index c15b68a..002deb0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(bin_files
   ${bin_files}
   ${CMAKE_CURRENT_SOURCE_DIR}/fix-paje-trace.sh
index b3c5671..db2676b 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl
+#!/usr/bin/env perl
 
 # Copyright (c) 2005, 2007, 2010, 2014. The SimGrid Team.
 # All rights reserved.
index cd23d39..2ac7c85 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2006-2007, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,8 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
+
 #use Data::Dumper;
 use XFig;
 use POSIX;
index c816648..7771c98 100644 (file)
@@ -34,11 +34,6 @@ SET(CTEST_PROJECT_NAME "${PROJECT_NAME}")
 SET(CTEST_CUSTOM_MAXIMUM_FAILED_TEST_OUTPUT_SIZE "3000000")
 SET(CTEST_CUSTOM_MAXIMUM_PASSED_TEST_OUTPUT_SIZE "3000000")
 
-set(PIPOL_IMAGE $ENV{PIPOL_IMAGE})
-if(NOT ${PIPOL_IMAGE} MATCHES "\n")
-  set(SITE ${PIPOL_IMAGE})
-endif()
-
 set(PATTERN_CTEST_IGNORED "")
 if(enable_coverage)
     set(PATTERN_CTEST_IGNORED 
index 1b37d52..e695dcf 100644 (file)
@@ -17,7 +17,11 @@ IF(CMAKE_SYSTEM_PROCESSOR MATCHES ".86|AMD64|amd64")
     message(STATUS "System processor: x86_64 (${CMAKE_SYSTEM_PROCESSOR}, 64 bits)")
     set(PROCESSOR_x86_64 1)
   ENDIF()
-  set(HAVE_RAWCTX 1)
+  if (MSVC)
+    message(STATUS "Disable fast raw contextes on Microsoft Visual.")
+  else()
+    set(HAVE_RAWCTX 1)
+  endif()
 
 ELSEIF(CMAKE_SYSTEM_PROCESSOR MATCHES "^alpha")
   message(STATUS "System processor: alpha")
@@ -62,13 +66,12 @@ else()
   set(MPI_ADDRESS_SIZE 8)
 endif()
 
-message(STATUS "Cmake version ${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION}")
-
 include(CheckFunctionExists)
 include(CheckTypeSize)
 include(CheckIncludeFile)
 include(CheckIncludeFiles)
 include(CheckLibraryExists)
+include(CheckSymbolExists)
 include(TestBigEndian)
 TEST_BIG_ENDIAN(BIGENDIAN)
 
@@ -148,20 +151,19 @@ CHECK_LIBRARY_EXISTS(rt      clock_gettime           "" HAVE_POSIX_GETTIME)
 
 if(CMAKE_SYSTEM_NAME MATCHES "Darwin")
   set(CMAKE_REQUIRED_DEFINITIONS "-D_XOPEN_SOURCE=700 -D_DARWIN_C_SOURCE")
+elseif(MINGW)
+  add_definitions(-D__USE_MINGW_ANSI_STDIO=1)
+  set(CMAKE_REQUIRED_DEFINITIONS "-D__USE_MINGW_ANSI_STDIO=1")
+else()
+  set(CMAKE_REQUIRED_DEFINITIONS "-D_GNU_SOURCE")
 endif()
 
-CHECK_INCLUDE_FILES("time.h;sys/time.h" TIME_WITH_SYS_TIME)
 CHECK_INCLUDE_FILES("stdlib.h;stdarg.h;string.h;float.h" STDC_HEADERS)
-CHECK_INCLUDE_FILE("pthread.h" HAVE_PTHREAD_H)
 CHECK_INCLUDE_FILE("valgrind/valgrind.h" HAVE_VALGRIND_VALGRIND_H)
 CHECK_INCLUDE_FILE("socket.h" HAVE_SOCKET_H)
-CHECK_INCLUDE_FILE("sys/socket.h" HAVE_SYS_SOCKET_H)
 CHECK_INCLUDE_FILE("stat.h" HAVE_STAT_H)
 CHECK_INCLUDE_FILE("sys/stat.h" HAVE_SYS_STAT_H)
 CHECK_INCLUDE_FILE("windows.h" HAVE_WINDOWS_H)
-CHECK_INCLUDE_FILE("winsock.h" HAVE_WINSOCK_H)
-CHECK_INCLUDE_FILE("winsock2.h" HAVE_WINSOCK2_H)
-CHECK_INCLUDE_FILE("windef.h" HAVE_WINDEF_H)
 CHECK_INCLUDE_FILE("errno.h" HAVE_ERRNO_H)
 CHECK_INCLUDE_FILE("unistd.h" HAVE_UNISTD_H)
 CHECK_INCLUDE_FILE("execinfo.h" HAVE_EXECINFO_H)
@@ -170,10 +172,6 @@ CHECK_INCLUDE_FILE("sys/time.h" HAVE_SYS_TIME_H)
 CHECK_INCLUDE_FILE("sys/param.h" HAVE_SYS_PARAM_H)
 CHECK_INCLUDE_FILE("sys/sysctl.h" HAVE_SYS_SYSCTL_H)
 CHECK_INCLUDE_FILE("time.h" HAVE_TIME_H)
-CHECK_INCLUDE_FILE("inttypes.h" HAVE_INTTYPES_H)
-CHECK_INCLUDE_FILE("memory.h" HAVE_MEMORY_H)
-CHECK_INCLUDE_FILE("stdlib.h" HAVE_STDLIB_H)
-CHECK_INCLUDE_FILE("strings.h" HAVE_STRINGS_H)
 CHECK_INCLUDE_FILE("string.h" HAVE_STRING_H)
 CHECK_INCLUDE_FILE("ucontext.h" HAVE_UCONTEXT_H)
 CHECK_INCLUDE_FILE("stdio.h" HAVE_STDIO_H)
@@ -186,15 +184,24 @@ CHECK_FUNCTION_EXISTS(sysconf HAVE_SYSCONF)
 CHECK_FUNCTION_EXISTS(readv HAVE_READV)
 CHECK_FUNCTION_EXISTS(popen HAVE_POPEN)
 CHECK_FUNCTION_EXISTS(signal HAVE_SIGNAL)
-CHECK_FUNCTION_EXISTS(snprintf HAVE_SNPRINTF)
-CHECK_FUNCTION_EXISTS(vsnprintf HAVE_VSNPRINTF)
-CHECK_FUNCTION_EXISTS(asprintf HAVE_ASPRINTF)
-CHECK_FUNCTION_EXISTS(vasprintf HAVE_VASPRINTF)
+
+CHECK_SYMBOL_EXISTS(snprintf stdio.h HAVE_SNPRINTF)
+CHECK_SYMBOL_EXISTS(vsnprintf stdio.h HAVE_VSNPRINTF)
+CHECK_SYMBOL_EXISTS(asprintf stdio.h HAVE_ASPRINTF)
+CHECK_SYMBOL_EXISTS(vasprintf stdio.h HAVE_VASPRINTF)
+
+if(MINGW) 
+  # The detection of asprintf fails on MinGW, assumingly because it's
+  # defined as an inline function in stdio.h instead of a regular
+  # function. So force the result to be 1 despite of the test.
+  set(HAVE_ASPRINTF 1)
+  set(HAVE_VASPRINTF 1)
+endif()
+
 CHECK_FUNCTION_EXISTS(makecontext HAVE_MAKECONTEXT)
-CHECK_FUNCTION_EXISTS(mmap HAVE_MMAP)
 CHECK_FUNCTION_EXISTS(process_vm_readv HAVE_PROCESS_VM_READV)
-CHECK_FUNCTION_EXISTS(strdup SIMGRID_HAVE_STRDUP)
-CHECK_FUNCTION_EXISTS(_strdup SIMGRID_HAVE__STRDUP)
+
+CHECK_FUNCTION_EXISTS(mmap HAVE_MMAP)
 
 #Check if __thread is defined
 execute_process(
@@ -210,7 +217,11 @@ else()
 endif()
 
 # Our usage of mmap is Linux-specific (flag MAP_ANONYMOUS), but kFreeBSD uses a GNU libc
-IF(NOT "${CMAKE_SYSTEM}" MATCHES "Linux" AND NOT "${CMAKE_SYSTEM}" MATCHES "kFreeBSD" AND NOT "${CMAKE_SYSTEM}" MATCHES "GNU" AND NOT  "${CMAKE_SYSTEM}" MATCHES "Darwin")
+IF(HAVE_MMAP AND
+   NOT "${CMAKE_SYSTEM}" MATCHES "Linux" AND 
+   NOT "${CMAKE_SYSTEM}" MATCHES "kFreeBSD" AND 
+   NOT "${CMAKE_SYSTEM}" MATCHES "GNU" AND 
+   NOT  "${CMAKE_SYSTEM}" MATCHES "Darwin")
   SET(HAVE_MMAP 0)
   message(STATUS "Warning: MMAP is thought as non functional on this architecture (${CMAKE_SYSTEM})")
 ENDIF()
@@ -222,7 +233,7 @@ else()
 endif()
 
 
-if(WIN32) #THOSE FILES ARE FUNCTIONS ARE NOT DETECTED BUT THEY SHOULD...
+if(WIN32) # Those files are not detected despite being present
   set(HAVE_UCONTEXT_H 1)
   set(HAVE_MAKECONTEXT 1)
   set(HAVE_SNPRINTF 1)
@@ -275,11 +286,6 @@ if(enable_smpi)
   endif()
 endif()
 
-#--------------------------------------------------------------------------------------------------
-### Check for some architecture dependent values
-CHECK_TYPE_SIZE(int SIZEOF_INT)
-CHECK_TYPE_SIZE(void* SIZEOF_VOIDP)
-
 #--------------------------------------------------------------------------------------------------
 ### Check for GNU dynamic linker
 CHECK_INCLUDE_FILE("dlfcn.h" HAVE_DLFCN_H)
@@ -320,12 +326,6 @@ endif()
 #--------------------------------------------------------------------------------------------------
 ### Initialize of CONTEXT THREADS
 
-if(HAVE_PTHREAD)
-  set(pthread 1)
-elseif(pthread)
-  set(pthread 0)
-endif()
-
 if(HAVE_PTHREAD)
   ### Test that we have a way to create semaphores
 
index b94ebb9..e34d7e3 100644 (file)
@@ -87,7 +87,6 @@ set(EXTRA_DIST
   src/surf/host_clm03.hpp
   src/surf/host_interface.hpp
   src/surf/host_ptask_L07.hpp
-  src/win32/config.h
   src/xbt/automaton/automaton_lexer.yy.c
   src/xbt/automaton/parserPromela.lex
   src/xbt/automaton/parserPromela.tab.cacc
@@ -266,7 +265,7 @@ set(XBT_SRC
   src/xbt/lib.c
   src/xbt/log.c
   src/xbt/mallocator.c
-  src/xbt/parmap.c
+  src/xbt/parmap.cpp
   src/xbt/set.c
   src/xbt/setset.c
   src/xbt/snprintf.c
@@ -277,6 +276,7 @@ set(XBT_SRC
   src/xbt/xbt_main.c
   src/xbt/xbt_matrix.c
   src/xbt/xbt_os_time.c
+  src/xbt/xbt_os_file.c
   src/xbt/xbt_peer.c
   src/xbt/xbt_queue.c
   src/xbt/xbt_replay.c
@@ -353,7 +353,6 @@ set(SIMIX_SRC
   src/simix/libsmx.c
   src/simix/smx_context.c
   src/simix/smx_context_base.c
-  src/simix/smx_context_raw.c
   src/simix/smx_deployment.c
   src/simix/smx_environment.c
   src/simix/smx_global.c
@@ -368,6 +367,18 @@ set(SIMIX_SRC
   ${SIMIX_GENERATED_SRC}
   )
 
+# Don't try to compile our inline assembly with MSVC
+if (MSVC)
+  set(EXTRA_DIST
+      ${EXTRA_DIST}
+      src/simix/smx_context_raw.c)
+else()
+  set(SIMIX_SRC
+      ${SIMIX_SRC}
+      src/simix/smx_context_raw.c)
+endif()
+
+# Boost context may not be available
 if (HAVE_BOOST_CONTEXT)
   set(SIMIX_SRC
       ${SIMIX_SRC}
@@ -616,8 +627,8 @@ set(MC_SRC
 
   src/mc/mc_forward.h
   src/mc/mc_forward.hpp
-  src/mc/mc_process.h
-  src/mc/mc_process.cpp
+  src/mc/Process.hpp
+  src/mc/Process.cpp
   src/mc/mc_unw.h
   src/mc/mc_unw.cpp
   src/mc/mc_unw_vmread.cpp
@@ -632,6 +643,7 @@ set(MC_SRC
   src/mc/mc_comm_determinism.cpp
   src/mc/mc_compare.cpp
   src/mc/mc_diff.cpp
+  src/mc/mc_dwarf.hpp
   src/mc/mc_dwarf.cpp
   src/mc/mc_dwarf_attrnames.cpp
   src/mc/mc_dwarf_expression.cpp
@@ -722,6 +734,7 @@ set(headers_to_install
   include/xbt/dynar.h
   include/xbt/ex.h
   include/xbt/fifo.h
+  include/xbt/file.h
   include/xbt/function_types.h
   include/xbt/graph.h
   include/xbt/graphxml.h
@@ -888,6 +901,7 @@ set(DOC_SOURCES
   doc/doxygen/deployment.doc
   doc/doxygen/footer.html
   doc/doxygen/getting_started.doc
+  doc/doxygen/getting_started_index.doc
   doc/doxygen/header.html
   doc/doxygen/help.doc
   doc/doxygen/index.doc
@@ -912,7 +926,7 @@ set(DOC_SOURCES
   doc/doxygen/pls.doc
   doc/doxygen/stylesheet.css
   doc/doxygen/tracing.doc
-  doc/doxygen/use.doc
+  doc/doxygen/examples.doc
 
   doc/manpage/smpicc.1
   doc/manpage/smpicxx.1
@@ -948,6 +962,7 @@ set(DOC_TOOLS
   tools/doxygen/fig2dev_postprocessor.pl
   tools/doxygen/index_create.pl
   tools/doxygen/xbt_log_extract_hierarchy.pl
+  tools/doxygen/list_routing_models_examples.sh
   )
 
 # these files get copied automatically to the html documentation
@@ -963,6 +978,7 @@ set(DOC_IMG
   ${CMAKE_HOME_DIRECTORY}/doc/webcruft/awstats_logo3.png
   ${CMAKE_HOME_DIRECTORY}/doc/webcruft/output.goal.pdf
   ${CMAKE_HOME_DIRECTORY}/doc/webcruft/poster_thumbnail.png
+  ${CMAKE_HOME_DIRECTORY}/doc/webcruft/storage_sample_scenario.png
   ${CMAKE_HOME_DIRECTORY}/doc/webcruft/simgrid_logo_2011.gif
   ${CMAKE_HOME_DIRECTORY}/doc/webcruft/simgrid_logo_2011.png
   ${CMAKE_HOME_DIRECTORY}/doc/webcruft/simgrid_logo_2011_small.png
@@ -1182,18 +1198,17 @@ set(TOOLS_CMAKEFILES_TXT
 
 set(CMAKE_SOURCE_FILES
   CMakeLists.txt
-  tools/cmake/AddTests.cmake
+  tools/cmake/Tests.cmake
   tools/cmake/CTestConfig.cmake
   tools/cmake/CTestCustom.cmake
   tools/cmake/CompleteInFiles.cmake
   tools/cmake/DefinePackages.cmake
   tools/cmake/Distrib.cmake
-  tools/cmake/Flags.cmake
-  tools/cmake/GenerateDoc.cmake
-  tools/cmake/GenerateDocWin.cmake
+  tools/cmake/GCCFlags.cmake
+  tools/cmake/Documentation.cmake
   tools/cmake/MaintainerMode.cmake
   tools/cmake/MakeExe.cmake
-  tools/cmake/MakeJava.cmake
+  tools/cmake/Java.cmake
   tools/cmake/MakeLib.cmake
   tools/cmake/MakeLibWin.cmake
   tools/cmake/Modules/FindGFortran.cmake
@@ -1209,17 +1224,22 @@ set(CMAKE_SOURCE_FILES
   tools/cmake/Modules/FindSimGrid.cmake
   tools/cmake/Modules/FindValgrind.cmake
   tools/cmake/Option.cmake
-  tools/cmake/Pipol.cmake
   tools/cmake/PrintArgs.cmake
-  tools/cmake/Scripts/Diff.pm
-  tools/cmake/Scripts/Makefile.default
-  tools/cmake/Scripts/SimGrid.packproj
-  tools/cmake/Scripts/generate_memcheck_tests.pl
-  tools/cmake/Scripts/java_bundle.sh
-  tools/cmake/Scripts/my_valgrind.pl
-  tools/cmake/Scripts/postinstall.sh
-  tools/cmake/Scripts/preinstall.sh
-  tools/cmake/Scripts/update_tesh.pl
+  tools/cmake/scripts/IPC/Run.pm
+  tools/cmake/scripts/IPC/Run/Debug.pm
+  tools/cmake/scripts/IPC/Run/IO.pm
+  tools/cmake/scripts/IPC/Run/Timer.pm
+  tools/cmake/scripts/IPC/Run/Win32Helper.pm
+  tools/cmake/scripts/IPC/Run/Win32IO.pm
+  tools/cmake/scripts/IPC/Run/Win32Pump.pm
+  tools/cmake/scripts/Diff.pm
+  tools/cmake/scripts/Makefile.default
+  tools/cmake/scripts/SimGrid.packproj
+  tools/cmake/scripts/generate_memcheck_tests.pl
+  tools/cmake/scripts/my_valgrind.pl
+  tools/cmake/scripts/postinstall.sh
+  tools/cmake/scripts/preinstall.sh
+  tools/cmake/scripts/update_tesh.pl
   tools/cmake/UnitTesting.cmake
   tools/cmake/src/internal_config.h.in
   tools/cmake/src/simgrid.nsi.in
@@ -1234,7 +1254,7 @@ set(CMAKE_SOURCE_FILES
   tools/cmake/test_prog/prog_stacksetup.c
   tools/cmake/test_prog/prog_thread_storage.c
   tools/cmake/test_prog/prog_vsnprintf.c
-  buildtools/Cross/Mingw.cmake
+  tools/cmake/cross-mingw.cmake
   tools/stack-cleaner/as
   tools/stack-cleaner/cc
   tools/stack-cleaner/c++
index 9e96457..afa1426 100644 (file)
@@ -9,29 +9,6 @@ install(DIRECTORY "${CMAKE_HOME_DIRECTORY}/doc/html/"
 install(DIRECTORY "${CMAKE_HOME_DIRECTORY}/doc/HelloWorld/"
   DESTINATION $ENV{DESTDIR}${CMAKE_INSTALL_PREFIX}/doc/simgrid/HelloWorld/)
 
-#### Generate the manpages
-if(NOT WIN32)
-  if( NOT MANPAGE_DIR)
-    set( MANPAGE_DIR ${CMAKE_BINARY_DIR}/manpages )
-  endif()
-
-  add_custom_target(manpages ALL
-    COMMAND ${CMAKE_COMMAND} -E make_directory ${MANPAGE_DIR}
-    COMMAND pod2man ${CMAKE_HOME_DIRECTORY}/tools/simgrid_update_xml.pl > ${MANPAGE_DIR}/simgrid_update_xml.1
-    COMMENT "Generating manpages"
-    )
-  install(FILES
-    ${MANPAGE_DIR}/simgrid_update_xml.1
-    ${CMAKE_HOME_DIRECTORY}/tools/tesh/tesh.1
-    ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpicc.1
-    ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpicxx.1
-    ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpif90.1
-    ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpiff.1
-    ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpirun.1
-    DESTINATION $ENV{DESTDIR}${CMAKE_INSTALL_PREFIX}/share/man/man1)
-
-endif()
-
 # binaries
 if(enable_smpi)
   install(PROGRAMS
@@ -81,11 +58,7 @@ if(enable_lib_static AND NOT WIN32)
 endif()
 
 if(enable_java)
-  if(enable_lib_in_jar)
-    set(SIMGRID_JAR_TO_INSTALL "${SIMGRID_FULL_JAR}")
-  else()
-    set(SIMGRID_JAR_TO_INSTALL "${SIMGRID_JAR}")
-  endif()
+  set(SIMGRID_JAR_TO_INSTALL "${SIMGRID_JAR}")
   install(TARGETS simgrid-java
       DESTINATION $ENV{DESTDIR}${CMAKE_INSTALL_PREFIX}/lib/)
   install(FILES ${SIMGRID_JAR_TO_INSTALL}
@@ -278,7 +251,7 @@ endforeach(file ${source_to_pack})
 
 add_custom_command(
   TARGET dist-dir
-  COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_HOME_DIRECTORY}/tools/cmake/Scripts/Makefile.default ${PROJECT_NAME}-${release_version}/Makefile
+  COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_HOME_DIRECTORY}/tools/cmake/scripts/Makefile.default ${PROJECT_NAME}-${release_version}/Makefile
   COMMAND ${CMAKE_COMMAND} -E echo "${GIT_VERSION}" > ${PROJECT_NAME}-${release_version}/.gitversion
   )
 
@@ -391,4 +364,18 @@ add_custom_target(maintainer-clean
   WORKING_DIRECTORY "${CMAKE_HOME_DIRECTORY}"
   )
 
+if(WIN32)
+  find_program(NSIS_PROGRAM NAMES makensi)
+  message(STATUS "nsis: ${NSIS_PROGRAM}")
+
+  if(NSIS_PROGRAM)
+    ADD_CUSTOM_TARGET(nsis
+      COMMENT "Generating the SimGrid installer for Windows..."
+      DEPENDS simgrid simgrid graphicator simgrid-colorizer simgrid_update_xml
+      COMMAND ${NSIS_PROGRAM} simgrid.nsi
+      WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/
+    )
+  endif()
+endif()
+
 include(CPack)
similarity index 57%
rename from tools/cmake/GenerateDoc.cmake
rename to tools/cmake/Documentation.cmake
index 92a4c9b..038edc3 100644 (file)
@@ -1,4 +1,14 @@
-#### Generate the whole html documentation
+###
+### Generate all parts of the documentation on non-Windows systems
+###
+###   - HTML with doxygen (reference and manual)
+###   - Javadoc (reference)
+###   - manpages (reference of tools)
+###
+###  This file is not loaded on windows
+
+
+#### Generate the html documentation
 
 if (enable_documentation)
   find_package(Doxygen REQUIRED)
@@ -7,11 +17,6 @@ else()
   find_package(Doxygen)
 endif()
 
-if (HAVE_Java)
-  find_path(JAVADOC_PATH  NAMES javadoc   PATHS NO_DEFAULT_PATHS)
-  mark_as_advanced(JAVADOC_PATH)
-endif()
-
 find_path(FIG2DEV_PATH  NAMES fig2dev  PATHS NO_DEFAULT_PATHS)
 
 
@@ -70,20 +75,23 @@ if(DOXYGEN_FOUND)
     COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/index_create.pl simgrid.tag index-API.doc
     COMMAND ${CMAKE_COMMAND} -E remove ${CMAKE_HOME_DIRECTORY}/doc/doxygen/logcategories.doc
     COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/xbt_log_extract_hierarchy.pl > ${CMAKE_HOME_DIRECTORY}/doc/doxygen/logcategories.doc
+    COMMAND ${CMAKE_COMMAND} -E echo "XX Generate list of files in examples/ for routing models"
+    COMMAND ${CMAKE_COMMAND} -E make_directory ${CMAKE_HOME_DIRECTORY}/doc/example_lists/
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh Floyd > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_floyd
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh Dijkstra > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_dijkstra
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh DijkstraCache > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_dijkstra_cache
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh 'routing="None"' > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_none
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh 'routing="Cluster"' > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_cluster
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh 'routing="Vivaldi"' > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_vivaldi
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh 'routing="Full"' > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_routing_full
+    COMMAND ${CMAKE_COMMAND} -E echo "XX Generate list of files in examples/ for XML tags"
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh '<mount ' > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_xmltag_mount
+    COMMAND ${CMAKE_HOME_DIRECTORY}/tools/doxygen/list_routing_models_examples.sh '<link_ctn ' > ${CMAKE_HOME_DIRECTORY}/doc/example_lists/example_filelist_xmltag_linkctn
     COMMAND ${CMAKE_COMMAND} -E echo "XX Run doxygen again"
     COMMAND ${DOXYGEN_EXECUTABLE} Doxyfile
     COMMAND ${CMAKE_COMMAND} -E remove ${CMAKE_HOME_DIRECTORY}/doc/simgrid_modules.map
     WORKING_DIRECTORY ${CMAKE_HOME_DIRECTORY}/doc
     )
-    
-   if (HAVE_Java)
-      ADD_CUSTOM_COMMAND(TARGET doc
-        COMMAND ${CMAKE_COMMAND} -E echo "XX Javadoc pass"
-        COMMAND ${JAVADOC_PATH}/javadoc -quiet -d ${CMAKE_HOME_DIRECTORY}/doc/html/javadoc/ ${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/*.java ${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/*/*.java
-        WORKING_DIRECTORY ${CMAKE_HOME_DIRECTORY}/doc
-      )
-   endif()
-       
 
 
 
@@ -111,5 +119,38 @@ add_custom_target(sync-gforge-dtd
   WORKING_DIRECTORY "${CMAKE_HOME_DIRECTORY}"
   )
 
+endif() # Doxygen found
+
+
+if (HAVE_Java)
+  find_path(JAVADOC_PATH  NAMES javadoc   PATHS NO_DEFAULT_PATHS)
+  mark_as_advanced(JAVADOC_PATH)
+  
+  ADD_CUSTOM_COMMAND(TARGET doc
+    COMMAND ${CMAKE_COMMAND} -E echo "XX Javadoc pass"
+    COMMAND ${JAVADOC_PATH}/javadoc -quiet -d ${CMAKE_HOME_DIRECTORY}/doc/html/javadoc/ ${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/*.java ${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/*/*.java
+    WORKING_DIRECTORY ${CMAKE_HOME_DIRECTORY}/doc
+  )
+endif()
+       
+#### Generate the manpages
+if( NOT MANPAGE_DIR)
+  set( MANPAGE_DIR ${CMAKE_BINARY_DIR}/manpages )
 endif()
 
+add_custom_target(manpages ALL
+  COMMAND ${CMAKE_COMMAND} -E make_directory ${MANPAGE_DIR}
+  COMMAND pod2man ${CMAKE_HOME_DIRECTORY}/tools/simgrid_update_xml.pl > ${MANPAGE_DIR}/simgrid_update_xml.1
+  COMMAND pod2man ${CMAKE_HOME_DIRECTORY}/tools/tesh/tesh.pl > ${MANPAGE_DIR}/tesh.1
+  COMMENT "Generating manpages"
+  )
+install(FILES
+  ${MANPAGE_DIR}/simgrid_update_xml.1
+  ${MANPAGE_DIR}/tesh.1
+  ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpicc.1
+  ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpicxx.1
+  ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpif90.1
+  ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpiff.1
+  ${CMAKE_HOME_DIRECTORY}/doc/manpage/smpirun.1
+  DESTINATION $ENV{DESTDIR}${CMAKE_INSTALL_PREFIX}/share/man/man1)
+
similarity index 56%
rename from tools/cmake/Flags.cmake
rename to tools/cmake/GCCFlags.cmake
index a11db3d..11d5caf 100644 (file)
@@ -1,6 +1,8 @@
 ##
 ## This file is in charge of setting our paranoid flags with regard to warnings and optimization.
 ##
+##   It is only used for gcc and clang. MSVC builds don't load this file.
+##
 ##   These flags do break some classical CMake tests, so you don't
 ##   want to do so before the very end of the configuration.
 ## 
@@ -30,35 +32,67 @@ if(enable_compile_warnings)
   set(CMAKE_JAVA_COMPILE_FLAGS "-Xlint")
 endif()
 
+# Se the optimisation flags
+# NOTE, we should CMAKE_BUILD_TYPE for this
 if(enable_compile_optimizations)
   set(optCFLAGS "-O3 -funroll-loops -fno-strict-aliasing ")
-  if(CMAKE_COMPILER_IS_GNUCC AND (NOT enable_model-checking))
-    set(optCFLAGS "${optCFLAGS} -finline-functions ")
+else()
+  set(optCFLAGS "-O0 ")
+endif()
+if(enable_compile_optimizations AND CMAKE_COMPILER_IS_GNUCC
+    AND (NOT enable_model-checking))
+  # This is redundant (already in -03):
+  set(optCFLAGS "${optCFLAGS} -finline-functions ")
+endif()
+
+# Configure LTO
+# NOTE, cmake 3.0 has a INTERPROCEDURAL_OPTIMIZATION target
+#       property for this (http://www.cmake.org/cmake/help/v3.0/prop_tgt/INTERPROCEDURAL_OPTIMIZATION.html)
+if(enable_lto) # User wants LTO. Try if we can do that
+  set(enable_lto OFF)
+  if(enable_compile_optimizations
+      AND CMAKE_COMPILER_IS_GNUCC
+      AND (NOT enable_model-checking))
     if(WIN32)
       if (COMPILER_C_VERSION_MAJOR_MINOR STRGREATER "4.8")
-      # On windows, we need 4.8 or higher to enable lto because of http://gcc.gnu.org/bugzilla/show_bug.cgi?id=50293
-      #
-      # We are experiencing assertion failures even with 4.8 on MinGW.
-      # Push the support forward: will see if 4.9 works when we test it.
-      set(optCFLAGS "${optCFLAGS} -flto ")
-      endif()
-    else()    
-      # On non-windows, 4.6 is enough for that
-      if(LINKER_VERSION STRGREATER "2.22")
-        set(optCFLAGS "${optCFLAGS} -flto ")
+        # On windows, we need 4.8 or higher to enable lto because of http://gcc.gnu.org/bugzilla/show_bug.cgi?id=50293
+        #
+        # We are experiencing assertion failures even with 4.8 on MinGW.
+        # Push the support forward: will see if 4.9 works when we test it.
+        set(enable_lto ON)
       endif()
+    elseif(LINKER_VERSION STRGREATER "2.22")
+      set(enable_lto ON)
+    endif()
+  endif()
+  if(enable_lto)
+    message("-- LTO seems usable.")
+  else()
+    if(NOT enable_compile_optimizations)
+      message("-- LTO disabled: Compile-time optimizations turned off.")
+    else() 
+      if(enable_model-checking)
+        message("-- LTO disabled when compiling with model-checking.")
+      else()
+        message("-- LTO does not seem usable -- try updating your build chain.")
+      endif() 
     endif()
   endif()
 else()
-  set(optCFLAGS "-O0 ")
-endif()
-
-if(enable_sdt)
-  add_definitions(-DUSE_SDT)
+  message("-- LTO disabled on the command line.")
 endif()
-
-if(enable_ust)
-  add_definitions(-DUSE_UST)
+if(enable_lto) # User wants LTO, and it seems usable. Go for it
+  set(optCFLAGS "${optCFLAGS} -flto ")
+  # See https://gcc.gnu.org/wiki/LinkTimeOptimizationFAQ#ar.2C_nm_and_ranlib:
+  # "Since version 4.9 gcc produces slim object files that only contain
+  # the intermediate representation. In order to handle archives of
+  # these objects you have to use the gcc wrappers:
+  # gcc-ar, gcc-nm and gcc-ranlib."
+  if(${CMAKE_C_COMPILER_ID} STREQUAL "GNU"
+      AND COMPILER_C_VERSION_MAJOR_MINOR STRGREATER "4.8")
+    set (CMAKE_AR gcc-ar)
+    set (CMAKE_RANLIB gcc-ranlib)
+  endif()
 endif()
 
 if(enable_model-checking AND enable_compile_optimizations)
@@ -133,3 +167,27 @@ if(NOT $ENV{LDFLAGS} STREQUAL "")
   message(STATUS "Add LDFLAGS: \"$ENV{LDFLAGS}\" to CMAKE_C_LINK_FLAGS")
   set(CMAKE_C_LINK_FLAGS "${CMAKE_C_LINK_FLAGS} $ENV{LDFLAGS}")
 endif()
+
+if(MINGW)
+  # http://stackoverflow.com/questions/10452262/create-64-bit-jni-under-windows
+  # We don't want to ship libgcc_s_seh-1.dll nor libstdc++-6.dll
+  set(CMAKE_C_FLAGS   "${CMAKE_C_FLAGS}   -static-libgcc")
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -static-libgcc -static-libstdc++")
+  set(CMAKE_SHARED_LIBRARY_LINK_C_FLAGS   "${CMAKE_SHARED_LIBRARY_LINK_C_FLAGS} -static-libgcc")
+  set(CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS "${CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS} -static-libgcc -static-libstdc++")
+  
+  # JNI searches for stdcalls
+  set(CMAKE_C_FLAGS   "${CMAKE_C_FLAGS}   -Wl,--add-stdcall-alias")
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wl,--add-stdcall-alias")
+  set(CMAKE_SHARED_LIBRARY_LINK_C_FLAGS "${CMAKE_SHARED_LIBRARY_LINK_C_FLAGS} -Wl,--add-stdcall-alias")
+  set(CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS "${CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS} -Wl,--add-stdcall-alias")
+  
+  # Specify the data model that we are using (yeah it may help Java)
+  if(ARCH_32_BITS) 
+    set(CMAKE_C_FLAGS   "${CMAKE_C_FLAGS}   -m32")
+    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -m32")
+  else()
+    set(CMAKE_C_FLAGS   "${CMAKE_C_FLAGS}   -m64")
+    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -m64")
+  endif()  
+endif()
diff --git a/tools/cmake/GenerateDocWin.cmake b/tools/cmake/GenerateDocWin.cmake
deleted file mode 100644 (file)
index bfac74b..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#### Generate the html documentation
-find_program(WGET_PROGRAM  NAMES wget)
-find_program(NSIS_PROGRAM NAMES makensi)
-
-message(STATUS "wget: ${WGET_PROGRAM}")
-message(STATUS "nsis: ${NSIS_PROGRAM}")
-
-if(WGET_PROGRAM)
-  ADD_CUSTOM_TARGET(simgrid_documentation
-    COMMENT "Downloading the SimGrid documentation..."
-    COMMAND ${WGET_PROGRAM} -r -np -nH -nd http://simgrid.gforge.inria.fr/simgrid/${release_version}/doc/
-    WORKING_DIRECTORY ${CMAKE_HOME_DIRECTORY}/doc/html
-    )
-endif()
-
-if(NSIS_PROGRAM)
-  ADD_CUSTOM_TARGET(nsis
-    COMMENT "Generating the SimGrid installer for Windows..."
-    DEPENDS simgrid simgrid graphicator simgrid-colorizer simgrid_update_xml
-    COMMAND ${NSIS_PROGRAM} simgrid.nsi
-    WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/
-    )
-endif()
diff --git a/tools/cmake/Java.cmake b/tools/cmake/Java.cmake
new file mode 100644 (file)
index 0000000..f480b95
--- /dev/null
@@ -0,0 +1,182 @@
+##
+## The Cmake definitions for the use of Java (and Scala)
+##   This file is loaded only if the Java option is activated
+##
+
+cmake_minimum_required(VERSION 2.8.6)
+
+find_package(Java 1.7 REQUIRED)
+include(UseJava)
+
+# Rules to build libsimgrid-java
+#
+add_library(simgrid-java SHARED ${JMSG_C_SRC})
+set_target_properties(simgrid-java PROPERTIES VERSION ${libsimgrid-java_version})
+if (CMAKE_VERSION VERSION_LESS "2.8.8")
+  include_directories(${JNI_INCLUDE_DIRS})
+
+  message("[Java] Try to workaround missing feature in older CMake. You should better update CMake to version 2.8.8 or above.")
+  get_directory_property(CHECK_INCLUDES INCLUDE_DIRECTORIES)
+else()
+  get_target_property(COMMON_INCLUDES simgrid-java INCLUDE_DIRECTORIES)
+  if (COMMON_INCLUDES)
+    set_target_properties(simgrid-java PROPERTIES
+      INCLUDE_DIRECTORIES "${COMMON_INCLUDES};${JNI_INCLUDE_DIRS}")
+  else()
+    set_target_properties(simgrid-java PROPERTIES
+      INCLUDE_DIRECTORIES "${JNI_INCLUDE_DIRS}")
+  endif()
+
+  get_target_property(CHECK_INCLUDES simgrid-java INCLUDE_DIRECTORIES)
+endif()
+message("-- [Java] simgrid-java includes: ${CHECK_INCLUDES}")
+
+target_link_libraries(simgrid-java simgrid)
+
+
+if(WIN32)
+  exec_program("java -d32 -version" OUTPUT_VARIABLE IS_32_BITS_JVM)
+  STRING( FIND ${IS_32_BITS_JVM} "Error" POSITION )
+  if(NOT ${POSITION} GREATER -1)
+    message(fatal_error "SimGrid can only use Java 64 bits")
+  endif()
+endif()
+
+# Rules to build simgrid.jar
+#
+
+## Files to include in simgrid.jar
+##
+set(SIMGRID_JAR "${CMAKE_BINARY_DIR}/simgrid.jar")
+set(MANIFEST_IN_FILE "${CMAKE_HOME_DIRECTORY}/src/bindings/java/MANIFEST.MF.in")
+set(MANIFEST_FILE "${CMAKE_BINARY_DIR}/src/bindings/java/MANIFEST.MF")
+
+set(LIBSIMGRID_SO
+  libsimgrid${CMAKE_SHARED_LIBRARY_SUFFIX})
+set(LIBSIMGRID_JAVA_SO
+  ${CMAKE_SHARED_LIBRARY_PREFIX}simgrid-java${CMAKE_SHARED_LIBRARY_SUFFIX})
+set(LIBSURF_JAVA_SO
+  ${CMAKE_SHARED_LIBRARY_PREFIX}surf-java${CMAKE_SHARED_LIBRARY_SUFFIX})
+
+## Here is how to build simgrid.jar
+##
+if(CMAKE_VERSION VERSION_LESS "2.8.12")
+  set(CMAKE_JAVA_TARGET_OUTPUT_NAME simgrid)
+  add_jar(simgrid-java_jar ${JMSG_JAVA_SRC})
+else()
+  add_jar(simgrid-java_jar ${JMSG_JAVA_SRC} OUTPUT_NAME simgrid)
+endif()
+
+add_custom_command(
+  TARGET simgrid-java_jar POST_BUILD
+  COMMENT "Add the documentation into simgrid.jar..."
+  DEPENDS ${MANIFEST_IN_FILE}
+         ${CMAKE_HOME_DIRECTORY}/COPYING
+         ${CMAKE_HOME_DIRECTORY}/ChangeLog
+         ${CMAKE_HOME_DIRECTORY}/NEWS
+         ${CMAKE_HOME_DIRECTORY}/ChangeLog.SimGrid-java
+         ${CMAKE_HOME_DIRECTORY}/LICENSE-LGPL-2.1
+           
+  COMMAND ${CMAKE_COMMAND} -E copy ${MANIFEST_IN_FILE} ${MANIFEST_FILE}
+  COMMAND ${CMAKE_COMMAND} -E echo "Specification-Version: \\\"${SIMGRID_VERSION_MAJOR}.${SIMGRID_VERSION_MINOR}.${SIMGRID_VERSION_PATCH}\\\"" >> ${MANIFEST_FILE}
+  COMMAND ${CMAKE_COMMAND} -E echo "Implementation-Version: \\\"${GIT_VERSION}\\\"" >> ${MANIFEST_FILE}
+
+  COMMAND ${Java_JAVADOC_EXECUTABLE} -quiet -d doc/javadoc -sourcepath ${CMAKE_HOME_DIRECTORY}/src/bindings/java/ org.simgrid.msg org.simgrid.surf org.simgrid.trace
+  
+  COMMAND ${JAVA_ARCHIVE} -uvmf ${MANIFEST_FILE} ${SIMGRID_JAR} doc/javadoc -C ${CMAKE_HOME_DIRECTORY} COPYING ChangeLog ChangeLog.SimGrid-java LICENSE-LGPL-2.1 NEWS
+  )
+
+###
+### Pack the java libraries into the jarfile if asked to do so
+###
+
+if(enable_lib_in_jar)
+  find_program(STRIP_COMMAND strip)
+  if(NOT STRIP_COMMAND)
+    set(STRIP_COMMAND "cmake -E echo (strip not found)")
+  endif()
+  set(SG_SYSTEM_NAME ${CMAKE_SYSTEM_NAME})
+  
+  if(${SG_SYSTEM_NAME} MATCHES "kFreeBSD")
+    set(SG_SYSTEM_NAME GNU/kFreeBSD)
+  endif()
+
+  set(JAVA_NATIVE_PATH NATIVE/${SG_SYSTEM_NAME}/${CMAKE_SYSTEM_PROCESSOR})
+  if(${CMAKE_SYSTEM_PROCESSOR} MATCHES "^i[3-6]86$")
+    set(JAVA_NATIVE_PATH NATIVE/${SG_SYSTEM_NAME}/x86)
+  endif()
+  if(  (${CMAKE_SYSTEM_PROCESSOR} MATCHES "x86_64") OR
+       (${CMAKE_SYSTEM_PROCESSOR} MATCHES "AMD64")     )
+    set(JAVA_NATIVE_PATH NATIVE/${SG_SYSTEM_NAME}/amd64)
+  endif()
+  if(${CMAKE_SYSTEM_PROCESSOR} MATCHES "armv7l")
+    set(JAVA_NATIVE_PATH NATIVE/${SG_SYSTEM_NAME}/arm) # Default arm (soft-float ABI)
+  endif()
+
+  add_custom_command(
+    TARGET simgrid-java_jar POST_BUILD
+    COMMENT "Add the native libs into simgrid.jar..."
+    DEPENDS simgrid-java 
+           ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_SO}
+           ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_JAVA_SO}
+           ${CMAKE_BINARY_DIR}/lib/${LIBSURF_JAVA_SO}
+         
+    COMMAND ${CMAKE_COMMAND} -E remove_directory NATIVE
+    COMMAND ${CMAKE_COMMAND} -E make_directory                                     ${JAVA_NATIVE_PATH}
+    COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_SO}      ${JAVA_NATIVE_PATH}
+    COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_JAVA_SO} ${JAVA_NATIVE_PATH}
+    COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_BINARY_DIR}/lib/${LIBSURF_JAVA_SO}    ${JAVA_NATIVE_PATH}
+    
+    # strip seems to fail on Mac on binaries that are already stripped.
+    # It then spits: "symbols referenced by indirect symbol table entries that can't be stripped"
+    COMMAND ${STRIP_COMMAND} ${JAVA_NATIVE_PATH}/${LIBSIMGRID_SO}      || true
+    COMMAND ${STRIP_COMMAND} ${JAVA_NATIVE_PATH}/${LIBSIMGRID_JAVA_SO} || true
+    COMMAND ${STRIP_COMMAND} ${JAVA_NATIVE_PATH}/${LIBSURF_JAVA_SO}    || true
+
+    COMMAND ${JAVA_ARCHIVE} -uvf ${SIMGRID_JAR}  NATIVE
+    COMMAND ${CMAKE_COMMAND} -E remove_directory NATIVE
+    
+    COMMAND ${CMAKE_COMMAND} -E echo "-- Cmake put the native code in ${JAVA_NATIVE_PATH}"
+    COMMAND "${Java_JAVA_EXECUTABLE}" -classpath "${SIMGRID_JAR}" org.simgrid.NativeLib
+    )
+  if(MINGW)
+    find_library(WINPTHREAD_DLL
+      NAME winpthread winpthread-1
+      PATHS C:\\MinGW C:\\MinGW64 C:\\MinGW\\bin C:\\MinGW64\\bin
+    )
+    add_custom_command(
+      TARGET simgrid-java_jar POST_BUILD
+      COMMENT "Add the MinGW libs into simgrid.jar..."
+      DEPENDS ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_SO}
+
+      COMMAND ${CMAKE_COMMAND} -E remove_directory NATIVE
+      COMMAND ${CMAKE_COMMAND} -E make_directory          ${JAVA_NATIVE_PATH}
+      COMMAND ${CMAKE_COMMAND} -E copy ${WINPTHREAD_DLL}  ${JAVA_NATIVE_PATH}
+
+      COMMAND ${JAVA_ARCHIVE} -uvf ${SIMGRID_JAR}  NATIVE
+      COMMAND ${CMAKE_COMMAND} -E remove_directory NATIVE
+    )
+  endif(MINGW)
+endif(enable_lib_in_jar)
+
+include_directories(${JNI_INCLUDE_DIRS} ${JAVA_INCLUDE_PATH} ${JAVA_INCLUDE_PATH2})
+
+if(enable_maintainer_mode)
+  set(CMAKE_SWIG_FLAGS "-package" "org.simgrid.surf")
+  set(CMAKE_SWIG_OUTDIR "${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/surf")
+
+  set_source_files_properties(${JSURF_SWIG_SRC} PROPERTIES CPLUSPLUS 1)
+
+  swig_add_module(surf-java java ${JSURF_SWIG_SRC} ${JSURF_JAVA_C_SRC})
+  swig_link_libraries(surf-java simgrid)
+else()
+  add_library(surf-java SHARED ${JSURF_C_SRC})
+  target_link_libraries(surf-java simgrid)
+endif()
+
+set_target_properties(surf-java PROPERTIES SKIP_BUILD_RPATH ON)
+set_target_properties(simgrid-java PROPERTIES SKIP_BUILD_RPATH ON)
+
+add_dependencies(simgrid-java surf-java)
+add_dependencies(simgrid-java_jar surf-java)
+
diff --git a/tools/cmake/MakeJava.cmake b/tools/cmake/MakeJava.cmake
deleted file mode 100644 (file)
index bb01398..0000000
+++ /dev/null
@@ -1,154 +0,0 @@
-cmake_minimum_required(VERSION 2.8.6)
-
-include(UseJava)
-
-# Rules to build libsimgrid-java
-#
-add_library(simgrid-java SHARED ${JMSG_C_SRC})
-set_target_properties(simgrid-java PROPERTIES VERSION ${libsimgrid-java_version})
-if (CMAKE_VERSION VERSION_LESS "2.8.8")
-  include_directories(${JNI_INCLUDE_DIRS})
-
-  message("[Java] Try to workaround missing feature in older CMake. You should better update CMake to version 2.8.8 or above.")
-  get_directory_property(CHECK_INCLUDES INCLUDE_DIRECTORIES)
-else()
-  get_target_property(COMMON_INCLUDES simgrid-java INCLUDE_DIRECTORIES)
-  if (COMMON_INCLUDES)
-    set_target_properties(simgrid-java PROPERTIES
-      INCLUDE_DIRECTORIES "${COMMON_INCLUDES};${JNI_INCLUDE_DIRS}")
-  else()
-    set_target_properties(simgrid-java PROPERTIES
-      INCLUDE_DIRECTORIES "${JNI_INCLUDE_DIRS}")
-  endif()
-
-  get_target_property(CHECK_INCLUDES simgrid-java INCLUDE_DIRECTORIES)
-endif()
-message("-- [Java] simgrid-java includes: ${CHECK_INCLUDES}")
-
-target_link_libraries(simgrid-java simgrid)
-
-
-if(WIN32)
-  exec_program("java -d32 -version"
-                OUTPUT_VARIABLE IS_32_BITS_JVM)
-  STRING( FIND ${IS_32_BITS_JVM} "Error" POSITION )
-  if(${POSITION} GREATER -1)
-    message("POTENTIAL ERROR: Java JVM needs to be 32 bits to be able to run with Simgrid on Windows for now")
-  endif()
-
-  set_target_properties(simgrid-java PROPERTIES
-    LINK_FLAGS "-Wl,--subsystem,windows,--kill-at"
-    PREFIX "")
-  find_path(PEXPORTS_PATH NAMES pexports.exe PATHS NO_DEFAULT_PATHS)
-  message(STATUS "pexports: ${PEXPORTS_PATH}")
-  if(PEXPORTS_PATH)
-    add_custom_command(TARGET simgrid-java POST_BUILD
-      COMMAND ${PEXPORTS_PATH}/pexports.exe ${CMAKE_BINARY_DIR}/lib/simgrid-java.dll > ${CMAKE_BINARY_DIR}/lib/simgrid-java.def)
-  endif(PEXPORTS_PATH)
-endif()
-
-# Rules to build simgrid.jar
-#
-
-## Files to include in simgrid.jar
-##
-set(SIMGRID_JAR "${CMAKE_BINARY_DIR}/simgrid.jar")
-set(SIMGRID_FULL_JAR "${CMAKE_BINARY_DIR}/simgrid_full.jar")
-set(MANIFEST_IN_FILE "${CMAKE_HOME_DIRECTORY}/src/bindings/java/MANIFEST.MF.in")
-set(MANIFEST_FILE "${CMAKE_BINARY_DIR}/src/bindings/java/MANIFEST.MF")
-
-
-set(LIBSIMGRID_SO
-  libsimgrid${CMAKE_SHARED_LIBRARY_SUFFIX})
-set(LIBSIMGRID_JAVA_SO
-  ${CMAKE_SHARED_LIBRARY_PREFIX}simgrid-java${CMAKE_SHARED_LIBRARY_SUFFIX})
-set(LIBSURF_JAVA_SO
-  ${CMAKE_SHARED_LIBRARY_PREFIX}surf-java${CMAKE_SHARED_LIBRARY_SUFFIX})
-
-## Don't strip libraries if not in release mode
-##
-if(release)
-  set(STRIP_COMMAND "${CMAKE_STRIP}")
-else()
-  set(STRIP_COMMAND "true")
-endif()
-
-## Here is how to build simgrid.jar
-##
-if(CMAKE_VERSION VERSION_LESS "2.8.12")
-  set(CMAKE_JAVA_TARGET_OUTPUT_NAME simgrid)
-  add_jar(simgrid-java_pre_jar ${JMSG_JAVA_SRC})
-else()
-  add_jar(simgrid-java_pre_jar ${JMSG_JAVA_SRC} OUTPUT_NAME simgrid)
-endif()
-
-set(JAVA_BUNDLE "${CMAKE_HOME_DIRECTORY}/tools/cmake/Scripts/java_bundle.sh")
-set(JAVA_BUNDLE_SO_FILES
-  ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_SO}
-  ${CMAKE_BINARY_DIR}/lib/${LIBSIMGRID_JAVA_SO}
-  ${CMAKE_BINARY_DIR}/lib/${LIBSURF_JAVA_SO}
-  )
-set(JAVA_BUNDLE_TXT_FILES
-  ${CMAKE_HOME_DIRECTORY}/COPYING
-  ${CMAKE_HOME_DIRECTORY}/ChangeLog
-  ${CMAKE_HOME_DIRECTORY}/ChangeLog.SimGrid-java
-  ${CMAKE_HOME_DIRECTORY}/LICENSE-LGPL-2.1
-  )
-add_custom_command(
-  COMMENT "Finalize simgrid.jar..."
-  OUTPUT ${SIMGRID_JAR}_finalized
-  DEPENDS simgrid simgrid-java simgrid-java_pre_jar
-          ${SIMGRID_JAR} ${MANIFEST_IN_FILE}
-          ${JAVA_BUNDLE_SO_FILES} ${JAVA_BUNDLE_TXT_FILES}
-  COMMAND ${JAVA_BUNDLE} "${SIMGRID_JAR}" "${Java_JAVA_EXECUTABLE}" "${STRIP_COMMAND}" -so ${JAVA_BUNDLE_SO_FILES} -txt ${JAVA_BUNDLE_TXT_FILES}
-  COMMAND ${CMAKE_COMMAND} -E copy ${MANIFEST_IN_FILE} ${MANIFEST_FILE}
-  COMMAND ${CMAKE_COMMAND} -E echo "Specification-Version: \\\"${SIMGRID_VERSION_MAJOR}.${SIMGRID_VERSION_MINOR}.${SIMGRID_VERSION_PATCH}\\\"" >> ${MANIFEST_FILE}
-  COMMAND ${CMAKE_COMMAND} -E echo "Implementation-Version: \\\"${GIT_VERSION}\\\"" >> ${MANIFEST_FILE}
-  COMMAND ${JAVA_ARCHIVE} -uvmf ${MANIFEST_FILE} ${SIMGRID_JAR}
-  COMMAND ${CMAKE_COMMAND} -E copy ${SIMGRID_JAR} ${SIMGRID_FULL_JAR}
-  COMMAND ${JAVA_ARCHIVE} -uvf ${SIMGRID_FULL_JAR} "NATIVE"
-  COMMAND ${CMAKE_COMMAND} -E remove ${SIMGRID_JAR}_finalized
-  COMMAND ${CMAKE_COMMAND} -E touch ${SIMGRID_JAR}_finalized
-  COMMAND ${Java_JAVADOC_EXECUTABLE} -quiet -d doc/javadoc ${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/*.java ${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/*/*.java
-  COMMAND ${JAVA_ARCHIVE} -uvf ${SIMGRID_FULL_JAR} doc/javadoc
-  )
-add_custom_target(simgrid-java_jar ALL DEPENDS ${SIMGRID_JAR}_finalized)
-
-include_directories(${JNI_INCLUDE_DIRS} ${JAVA_INCLUDE_PATH} ${JAVA_INCLUDE_PATH2})
-
-if(enable_maintainer_mode)
-  set(CMAKE_SWIG_FLAGS "-package" "org.simgrid.surf")
-  set(CMAKE_SWIG_OUTDIR "${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/surf")
-
-  set_source_files_properties(${JSURF_SWIG_SRC} PROPERTIES CPLUSPLUS 1)
-
-  swig_add_module(surf-java java ${JSURF_SWIG_SRC} ${JSURF_JAVA_C_SRC})
-
-  if(NOT "${CMAKE_BINARY_DIR}" STREQUAL "${CMAKE_BINARY_DIR}")
-    add_custom_command(TARGET surf-java POST_BUILD
-      COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_BINARY_DIR}/src/bindings/java/org/simgrid/surf/surfJAVA_wrap.cxx" "${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/surf/surfJAVA_wrap.cxx"
-      COMMAND ${CMAKE_COMMAND} -E copy "${CMAKE_BINARY_DIR}/src/bindings/java/org/simgrid/surf/surfJAVA_wrap.h" "${CMAKE_HOME_DIRECTORY}/src/bindings/java/org/simgrid/surf/surfJAVA_wrap.h"
-    )
-  endif()
-
-  swig_link_libraries(surf-java simgrid)
-else()
-  add_library(surf-java SHARED ${JSURF_C_SRC})
-  target_link_libraries(surf-java simgrid)
-endif()
-
-set_target_properties(surf-java PROPERTIES SKIP_BUILD_RPATH ON)
-set_target_properties(simgrid-java PROPERTIES SKIP_BUILD_RPATH ON)
-
-add_dependencies(simgrid-java surf-java)
-add_dependencies(simgrid-java_pre_jar surf-java)
-
-if(WIN32)
-  set_target_properties(surf-java PROPERTIES
-    LINK_FLAGS "-Wl,--subsystem,windows,--kill-at"
-    PREFIX "")
-  if(PEXPORTS_PATH)
-    add_custom_command(TARGET surf-java POST_BUILD
-      COMMAND ${PEXPORTS_PATH}/pexports.exe ${CMAKE_BINARY_DIR}/lib/surf-java.dll > ${CMAKE_BINARY_DIR}/lib/surf-java.def)
-  endif(PEXPORTS_PATH)
-endif()
index a240c3b..2fb2f46 100644 (file)
@@ -16,10 +16,6 @@ if(enable_ust)
   ADD_DEPENDENCIES(simgrid simgrid_ust)
 endif()
 
-if(enable_java)
-  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/MakeJava.cmake)
-endif()
-
 add_dependencies(simgrid maintainer_files)
 
 if(enable_model-checking)
@@ -37,27 +33,6 @@ if (HAVE_BOOST_CONTEXT)
   set(SIMGRID_DEP "${SIMGRID_DEP} ${Boost_CONTEXT_LIBRARY}")
 endif()
 
-if(${CMAKE_SYSTEM_NAME} STREQUAL "FreeBSD"
-    AND NOT ${CMAKE_SYSTEM_VERSION} VERSION_LESS 10.0
-    AND ${CMAKE_CXX_COMPILER_ID} STREQUAL "Clang")
-  # FreeBSD from 10.0 provide a internal C++ stack (unused by gcc)
-  # see https://wiki.freebsd.org/NewC%2B%2BStack
-  set(SIMGRID_DEP "${SIMGRID_DEP} -lc++")
-elseif(${CMAKE_SYSTEM_NAME} STREQUAL "FreeBSD"
-    AND ${CMAKE_SYSTEM_VERSION} VERSION_LESS 10.0
-    AND ${CMAKE_CXX_COMPILER_ID} STREQUAL "Clang")
-  # FreeBSD prior to 10.0 does not necessarily have a compiler
-  # installed that is capable of c++11! Hence, we just assume
-  # here that libc++ was compiled.
-  # FIXME: We should change this behavior; we may want to include
-  # an option of whether libc++ (clang++) or libstdc++ (g++)
-  # should be used.
-  include_directories( "/usr/local/include/c++/v1")
-  set(SIMGRID_DEP "${SIMGRID_DEP} -lc++ -L/usr/local/lib ")
-else()
-  set(SIMGRID_DEP "${SIMGRID_DEP} -lstdc++")
-endif()
-
 if(HAVE_PTHREAD AND ${CONTEXT_THREADS} AND NOT APPLE)
   # Clang on recent Mac OS X is not happy about -pthread.
   SET(SIMGRID_DEP "${SIMGRID_DEP} -pthread")
index 85a93cc..2a2a69a 100644 (file)
@@ -1,34 +1,25 @@
 ### Make Libs
-#>gcc c:\simgrid-trunk\examples\msg\icomms\peer.c -static -Lc:\simgrid-trunk\lib -lsimgrid -Ic:\simgrid-trunk\include -lwsock32
-
-if(enable_java)
-  include(${CMAKE_HOME_DIRECTORY}/tools/cmake/MakeJava.cmake)
-endif()
 
 add_library(simgrid SHARED ${simgrid_sources})
 
-set_target_properties(simgrid  PROPERTIES COMPILE_FLAGS "-D_XBT_DLL_EXPORT -DDLL_EXPORT" LINK_FLAGS "-shared" VERSION ${libsimgrid_version} PREFIX "lib" SUFFIX ".dll" IMPORT_PREFIX "lib" IMPORT_SUFFIX ".dll")
-
-set(SIMGRID_DEP "-lws2_32 -lm")
-
-if (HAVE_PTHREAD)
-  set(SIMGRID_DEP "${SIMGRID_DEP} -lpthread")
-endif()
-
-if(ARCH_32_BITS)
-  set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -m32 -march=i486 -D_I_X86_")
-  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -m32 -march=i486 -D_I_X86_")
+if(MSVC)
+  set_target_properties(simgrid  PROPERTIES 
+       COMPILE_FLAGS "/D_XBT_DLL_EXPORT /DDLL_EXPORT" 
+       VERSION ${libsimgrid_version} )
 else()
-  set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -m64 -D_AMD64_")
-  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -m64 -D_AMD64_")
-  #        message(FATAL_ERROR "Sorry, Simgrid fails with full 64bits for now! Please contact us.")
+  set_target_properties(simgrid  PROPERTIES 
+       COMPILE_FLAGS "-D_XBT_DLL_EXPORT -DDLL_EXPORT" 
+       LINK_FLAGS "-shared" 
+       VERSION ${libsimgrid_version} 
+       PREFIX "lib" SUFFIX ".dll" 
+       IMPORT_PREFIX "lib" IMPORT_SUFFIX ".dll")
+
+  set(SIMGRID_DEP "-lm")
+
+  if (HAVE_PTHREAD)
+    set(SIMGRID_DEP "${SIMGRID_DEP} -lpthread")
+  endif()
 endif()
 
 target_link_libraries(simgrid  ${SIMGRID_DEP})
 
-find_path(PEXPORTS_PATH NAMES pexports.exe PATHS NO_DEFAULT_PATHS)
-message(STATUS "pexports: ${PEXPORTS_PATH}")
-if(PEXPORTS_PATH)
-  add_custom_command(TARGET simgrid POST_BUILD
-    COMMAND ${PEXPORTS_PATH}/pexports.exe ${CMAKE_BINARY_DIR}/lib/libsimgrid.dll > ${CMAKE_BINARY_DIR}/lib/libsimgrid.def)
-endif()
index 2ab4e38..bc9f1f7 100644 (file)
@@ -11,8 +11,8 @@ find_program(VALGRIND_EXE
 
 if(VALGRIND_EXE)
   message(STATUS "Found valgrind: ${VALGRIND_EXE}")
-  SET(VALGRIND_COMMAND "${CMAKE_HOME_DIRECTORY}/tools/cmake/Scripts/my_valgrind.pl")
-  SET(MEMORYCHECK_COMMAND "${CMAKE_HOME_DIRECTORY}/tools/cmake/Scripts/my_valgrind.pl")
+  SET(VALGRIND_COMMAND "${CMAKE_HOME_DIRECTORY}/tools/cmake/scripts/my_valgrind.pl")
+  SET(MEMORYCHECK_COMMAND "${CMAKE_HOME_DIRECTORY}/tools/cmake/scripts/my_valgrind.pl")
 endif()
 
 if(enable_memcheck_xml)
@@ -24,7 +24,7 @@ if(VALGRIND_EXE)
   string(REGEX MATCH "[0-9].[0-9].[0-9]" NEW_VALGRIND_VERSION "${VALGRIND_VERSION}")
   if(NEW_VALGRIND_VERSION)
     message(STATUS "Valgrind version: ${NEW_VALGRIND_VERSION}")
-    exec_program("${CMAKE_HOME_DIRECTORY}/tools/cmake/Scripts/generate_memcheck_tests.pl ${CMAKE_HOME_DIRECTORY} ${CMAKE_HOME_DIRECTORY}/tools/cmake/AddTests.cmake > ${CMAKE_HOME_DIRECTORY}/tools/cmake/memcheck_tests.cmake" OUTPUT_VARIABLE SHUTT)
+    exec_program("${CMAKE_HOME_DIRECTORY}/tools/cmake/scripts/generate_memcheck_tests.pl ${CMAKE_HOME_DIRECTORY} ${CMAKE_HOME_DIRECTORY}/tools/cmake/Tests.cmake > ${CMAKE_HOME_DIRECTORY}/tools/cmake/memcheck_tests.cmake" OUTPUT_VARIABLE SHUTT)
     set(MEMORYCHECK_COMMAND_OPTIONS "--trace-children=yes --trace-children-skip=/usr/bin/*,/bin/* --leak-check=full --show-reachable=yes --track-origins=no --read-var-info=no --num-callers=20 --suppressions=${CMAKE_HOME_DIRECTORY}/tools/simgrid.supp ${VALGRIND_EXTRA_COMMAND_OPTIONS} ")
     message(STATUS "Valgrind options: ${MEMORYCHECK_COMMAND_OPTIONS}")
   else()
index 1116526..e6fb3e9 100644 (file)
@@ -9,9 +9,6 @@ else()
   set(CMAKE_INSTALL_PREFIX ${CMAKE_INSTALL_PREFIX} CACHE PATH "Path where this project should be installed")
 endif()
 
-set(pipol_user ${pipol_user} CACHE INTERNAL "pipol_user" FORCE)
-mark_as_advanced(pipol_user)
-
 option(release "Whether Release Mode is activated (disable tests on experimental parts)" on)
 option(enable_compile_optimizations "Whether to produce efficient code for the SimGrid library" on)
 option(enable_documentation "Whether to produce documentation" on)
@@ -23,20 +20,34 @@ option(enable_compile_warnings "Whether compilation warnings should be turned in
 option(enable_maintainer_mode "Whether flex and flexml files should be rebuilt." off)
 option(enable_tracing "Tracing simulations for visualization." on)
 option(enable_latency_bound_tracking "" off)
-option(enable_coverage "Whether coverage should be enabled." off)
+
 option(enable_ust "Enable userspace static tracepoint (lttng-ust)." off)
+if(enable_sdt)
+  add_definitions(-DUSE_SDT)
+endif()
+  
 option(enable_sdt "Enable statically defined tracepoint (strace/systemtap)." off)
+if(enable_ust)
+  add_definitions(-DUSE_UST)
+endif()
+    
+option(enable_coverage "Whether coverage should be enabled." off)
 mark_as_advanced(enable_coverage)
+mark_as_advanced(enable_memcheck)
+
 option(enable_memcheck "Enable memcheck." off)
 option(enable_memcheck_xml "Enable memcheck with xml output." off)
-mark_as_advanced(enable_memcheck)
 mark_as_advanced(enable_memcheck_xml)
+
 option(enable_mallocators "Enable mallocators (disable only for debugging purpose)." on)
+
 option(enable_print_message "Enable print message during config." off)
 mark_as_advanced(enable_print_message)
+
 option(enable_model-checking "Turn this on to experiment with our prototype of model-checker (hinders the simulation's performance even if turned off at runtime)" off)
 option(enable_lib_static "" off)
 option(enable_lib_in_jar "Whether the native libraries are bundled in a Java jar file" on)
+option(enable_lto "Whether we should try to activate the LTO (link time optimisation)" on)
 option(enable_jedule "Jedule output of SimDAG." off)
 option(enable_debug "Turn this off to remove all debug messages at compile time (faster, but no debug activatable)" on)
 option(enable_msg_deprecated "This option enables the use of deprecated MSG functions" off)
diff --git a/tools/cmake/Pipol.cmake b/tools/cmake/Pipol.cmake
deleted file mode 100644 (file)
index f1108fb..0000000
+++ /dev/null
@@ -1,171 +0,0 @@
-# On a Pipol system, set:
-# PIPOL_USER
-
-#SET(PIPOL_USER $ENV{PIPOL_USER})
-
-# ssh/rsync mandatory
-IF(pipol_user)
-
-  set(CMAKE_OPTIONS "  -Wno-dev")
-
-  if(with_context)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Dwith_context=${with_context}")
-  endif()
-
-  if(enable_smpi)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_smpi=on")
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_smpi_MPICH3_testsuite=on")
-  endif()
-
-  if(enable_lua)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_lua=on")
-  endif()
-
-  if(enable_compile_optimizations)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_compile_optimizations=on")
-  endif()
-
-  if(enable_compile_warnings)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_compile_warnings=on")
-  endif()
-
-  if(enable_tracing)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_tracing=on")
-  endif()
-
-  if(enable_coverage)
-    set(CMAKE_OPTIONS "${CMAKE_OPTION} -Denable_coverage=on")
-  endif()
-
-  if(enable_print_message)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_print_message=on")
-  endif()
-
-  if(enable_model-checking)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_model-checking=on")
-  endif()
-
-  if(enable_latency_bound_tracking)
-    set(CMAKE_OPTIONS "${CMAKE_OPTIONS}        -Denable_latency_bound_tracking=on")
-  endif()
-
-  FIND_PROGRAM(HAVE_SSH ssh)
-  FIND_PROGRAM(HAVE_RSYNC rsync)
-
-  MESSAGE(STATUS "Pipol user is '${pipol_user}'")
-  IF(HAVE_SSH)
-    message(STATUS "Found ssh: ${HAVE_SSH}")
-    # get pipol systems
-    EXECUTE_PROCESS(COMMAND
-      ssh ${pipol_user}@pipol.inria.fr pipol-sub --query=systems
-      OUTPUT_VARIABLE PIPOL_SYSTEMS OUTPUT_STRIP_TRAILING_WHITESPACE)
-
-  ENDIF()
-
-  ADD_CUSTOM_TARGET(pipol_test_list_images
-    COMMENT "Available images for pipol tests (cmake + make + make test) : "
-    )
-
-  ADD_CUSTOM_TARGET(pipol_experimental_list_images
-    COMMENT "Available images for ctest (ctest -D Experimental) : "
-    )
-
-  ADD_CUSTOM_TARGET(pipol_kvm_deploy
-    COMMENT "Deploy all kvm images on pipol (ctest -D Experimental) : "
-    )
-  ADD_CUSTOM_COMMAND(TARGET pipol_kvm_deploy
-    POST_BUILD
-    COMMENT "See results on http://cdash.inria.fr/CDash/index.php?project=Simgrid"
-    )
-
-  IF(HAVE_RSYNC)
-    message(STATUS "Found rsync: ${HAVE_RSYNC}")
-    MACRO(PIPOL_TARGET
-       SYSTEM_PATTERN)
-      STRING(REPLACE ".dd.gz" "" SYSTEM_TARGET ${SYSTEM_PATTERN})
-
-      ADD_CUSTOM_TARGET(
-       ${SYSTEM_TARGET}
-       COMMENT "PIPOL Build : ${SYSTEM_PATTERN}"
-       COMMAND rsync ${pipol_user}@pipol.inria.fr:/usr/local/bin/pipol-sub .
-       COMMAND ./pipol-sub --pipol-user=${pipol_user} ${SYSTEM_PATTERN} 02:00 --reconnect --group --keep --verbose=1 --export=${CMAKE_HOME_DIRECTORY} --rsynco=-aC
-       \"sudo chown ${pipol_user} ${CMAKE_HOME_DIRECTORY} \;
-       cd ${CMAKE_HOME_DIRECTORY} \;
-       sh ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/liste_install.sh \;
-       cmake -E remove CMakeCache.txt \;
-       cmake ${CMAKE_HOME_DIRECTORY}${CMAKE_OPTIONS} \;
-       make clean \;
-       make \;
-       make check \"
-       )
-      ADD_CUSTOM_TARGET(
-       ${SYSTEM_TARGET}_experimental
-       COMMENT "PIPOL Build : ${SYSTEM_PATTERN}_experimental"
-       COMMAND rsync ${pipol_user}@pipol.inria.fr:/usr/local/bin/pipol-sub .
-       COMMAND ./pipol-sub --pipol-user=${pipol_user} ${SYSTEM_PATTERN} 02:00 --reconnect --group --keep --verbose=1 --export=${CMAKE_HOME_DIRECTORY} --rsynco=-aC
-       \"sudo chown ${pipol_user} ${CMAKE_HOME_DIRECTORY} \;
-       cd ${CMAKE_HOME_DIRECTORY} \;
-       sh ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/liste_install.sh \;
-       cmake -E remove CMakeCache.txt \;
-       cmake ${CMAKE_HOME_DIRECTORY}${CMAKE_OPTIONS} \;
-       ctest -D Experimental \"
-       )
-
-      STRING(REGEX MATCH "kvm" make_test "${SYSTEM_TARGET}")
-      if(make_test)
-       STRING(REGEX MATCH "windows" make_test "${SYSTEM_TARGET}")
-       if(NOT make_test)
-         ADD_CUSTOM_COMMAND(TARGET pipol_kvm_deploy
-           COMMENT "PIPOL Build : ${SYSTEM_PATTERN}"
-           COMMAND rsync ${pipol_user}@pipol.inria.fr:/usr/local/bin/pipol-sub .
-           COMMAND ./pipol-sub --pipol-user=${pipol_user} ${SYSTEM_PATTERN} 02:00 --reconnect --group --keep --verbose=1 --export=${CMAKE_HOME_DIRECTORY} --rsynco=-aC
-           \"sudo chown ${pipol_user} ${CMAKE_HOME_DIRECTORY} \;
-           cd ${CMAKE_HOME_DIRECTORY} \;
-           sh ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/liste_install.sh \;
-           cmake -E remove CMakeCache.txt \;
-           cmake ${CMAKE_HOME_DIRECTORY}${CMAKE_OPTIONS} \;
-           ctest -D Experimental \"
-           )
-       endif()
-      endif()
-
-      ADD_CUSTOM_COMMAND(TARGET ${SYSTEM_TARGET}_experimental
-       POST_BUILD
-       COMMENT "See results on http://cdash.inria.fr/CDash/index.php?project=Simgrid"
-       )
-
-      ADD_CUSTOM_COMMAND(TARGET pipol_test_list_images
-       COMMAND echo ${SYSTEM_TARGET}
-       )
-    ADD_CUSTOM_COMMAND(TARGET pipol_experimental_list_images
-       COMMAND echo "${SYSTEM_TARGET}_experimental"
-       )
-    ENDMACRO(PIPOL_TARGET)
-
-  ENDIF()
-
-  # add a target for each pipol system
-  IF(PIPOL_SYSTEMS)
-    #MESSAGE(STATUS "Adding Pipol targets")
-    FOREACH(SYSTEM ${PIPOL_SYSTEMS})
-      PIPOL_TARGET(${SYSTEM})
-    ENDFOREACH(SYSTEM ${PIPOL_SYSTEMS})
-  ENDIF()
-
-  ADD_CUSTOM_TARGET(pipol_kill_all_jobs
-    COMMENT "PIPOL delete all jobs"
-    COMMAND ./pipol-sub --pipol-user=${pipol_user} deleteallmyjobs
-    )
-
-  #message(STATUS "Pipol options: ${CMAKE_OPTIONS}")
-
-  add_custom_target(sync-pipol
-  COMMENT "Update pipol script for user: ${pipol_user}"
-  COMMAND scp ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/rc.* ${pipol_user}@pipol.inria.fr:~/.pipol/
-  COMMAND scp ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/Nightly_simgrid.sh ${pipol_user}@pipol.inria.fr:~/.pipol/nightly/
-  COMMAND scp ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/Nightly_memCheck.sh ${pipol_user}@pipol.inria.fr:~/.pipol/nightly/
-  COMMAND scp ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/Experimental_bindings.sh ${pipol_user}@pipol.inria.fr:~/
-  COMMAND scp ${CMAKE_HOME_DIRECTORY}/buildtools/pipol/pre-simgrid.sh ${pipol_user}@pipol.inria.fr:~/
-  COMMAND ssh ${pipol_user}@pipol.inria.fr "chmod a=rwx ~/* ~/.pipol/rc.* ~/.pipol/nightly/*"
-  )
-ENDIF()
index ebbdf1a..e7ad433 100644 (file)
@@ -16,23 +16,18 @@ if(enable_print_message)
   message("\#define __VA_COPY_USE          ${__VA_COPY_USE}")
   message("HAVE_UCONTEXT ...............: ${HAVE_UCONTEXT}")
   message("")
-  message("HAVE_PTHREAD_CREATE .........: ${pthread}")
+  message("HAVE_PTHREAD ................: ${HAVE_PTHREAD}")
   message("HAVE_SEM_INIT ...............: ${HAVE_SEM_INIT_LIB}")
   message("HAVE_SEM_TIMEDWAIT ..........: ${HAVE_SEM_TIMEDWAIT_LIB}")
   message("HAVE_MUTEX_TIMEDLOCK ........: ${HAVE_MUTEX_TIMEDLOCK_LIB}")
   message("HAVE_POSIX_GETTIME ..........: ${HAVE_POSIX_GETTIME}")
   message("")
-  message("TIME_WITH_SYS_TIME ..........: ${TIME_WITH_SYS_TIME}")
   message("STDC_HEADERS ................: ${STDC_HEADERS}")
-  message("HAVE_PTHREAD_H ..............: ${HAVE_PTHREAD_H}")
   message("HAVE_VALGRIND_VALGRIND_H ....: ${HAVE_VALGRIND_VALGRIND_H}")
   message("HAVE_SOCKET_H ...............: ${HAVE_SOCKET_H}")
-  message("HAVE_SYS_SOCKET_H ...........: ${HAVE_SYS_SOCKET_H}")
   message("HAVE_STAT_H .................: ${HAVE_STAT_H}")
   message("HAVE_SYS_STAT_H .............: ${HAVE_SYS_STAT_H}")
   message("HAVE_WINDOWS_H ..............: ${HAVE_WINDOWS_H}")
-  message("HAVE_WINSOCK_H ..............: ${HAVE_WINSOCK_H}")
-  message("HAVE_WINSOCK2_H .............: ${HAVE_WINSOCK2_H}")
   message("HAVE_ERRNO_H ................: ${HAVE_ERRNO_H}")
   message("HAVE_UNISTD_H ...............: ${HAVE_UNISTD_H}")
   message("HAVE_EXECINFO_H .............: ${HAVE_EXECINFO_H}")
@@ -40,10 +35,6 @@ if(enable_print_message)
   message("HAVE_SYS_TIME_H .............: ${HAVE_SYS_TIME_H}")
   message("HAVE_TIME_H .................: ${HAVE_TIME_H}")
   message("HAVE_DLFCN_H ................: ${HAVE_DLFCN_H}")
-  message("HAVE_INTTYPES_H .............: ${HAVE_INTTYPES_H}")
-  message("HAVE_MEMORY_H ...............: ${HAVE_MEMORY_H}")
-  message("HAVE_STDLIB_H ...............: ${HAVE_STDLIB_H}")
-  message("HAVE_STRINGS_H ..............: ${HAVE_STRINGS_H}")
   message("HAVE_STRING_H ...............: ${HAVE_STRING_H}")
   message("HAVE_STDIO_H ................: ${HAVE_STDIO_H}")
 
@@ -102,6 +93,7 @@ message("")
 message("        CFlags ......................: ${CMAKE_C_FLAGS}")
 message("        CXXFlags ....................: ${CMAKE_CXX_FLAGS}")
 message("        LDFlags .....................: ${CMAKE_C_LINK_FLAGS}")
+message("        with LTO ....................: ${enable_lto}")
 message("")
 
 if (HAVE_NS3)
@@ -142,5 +134,3 @@ message("        INSTALL_PREFIX ..............: ${CMAKE_INSTALL_PREFIX}")
 exec_program("${CMAKE_COMMAND} -E make_directory ${PROJECT_BINARY_DIR}/Testing/Notes/" OUTPUT_VARIABLE OKIDOKI)
 file(WRITE ${PROJECT_BINARY_DIR}/Testing/Notes/Build  "GIT version : ${GIT_VERSION}\n")
 file(APPEND ${PROJECT_BINARY_DIR}/Testing/Notes/Build "Release     : simgrid-${release_version}\n")
-file(APPEND ${PROJECT_BINARY_DIR}/Testing/Notes/Build "Pipol user  : $ENV{PIPOL_USER}\n")
-file(APPEND ${PROJECT_BINARY_DIR}/Testing/Notes/Build "Pipol image : $ENV{PIPOL_IMAGE}\n")
diff --git a/tools/cmake/Scripts/java_bundle.sh b/tools/cmake/Scripts/java_bundle.sh
deleted file mode 100755 (executable)
index 38f663f..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-#!/bin/sh
-
-set -e
-#set -x
-
-if [ $# -lt 3 ]; then
-    cat >&2 <<EOF
-Usage: $0 simgrid.jar java_command strip_command [-so file.so...] [-txt file.txt...]
-    simgrid.jar    SimGrid jar file
-    java_command   path to the Java runtime
-    strip_command  path to the command used to strip libraries
-    file.so        library file to strip and bundle into the archive
-    file.txt       other file to bundle into the archive
-EOF
-    exit 1
-fi
-
-SIMGRID_JAR=$1
-JAVA=$2
-STRIP=$3
-shift 3
-
-JSG_BUNDLE=$("$JAVA" -classpath "$SIMGRID_JAR" org.simgrid.NativeLib --quiet)
-
-# sanity check
-case "$JSG_BUNDLE" in
-    NATIVE/*)
-        cat >&2 <<EOF
--- [Java] Native libraries bundled into: ${JSG_BUNDLE}
-EOF
-        ;;
-    *)
-        cat >&2 <<EOF
--- [Java] Native libraries NOT bundled into invalid directory: ${JSG_BUNDLE}
-EOF
-        exit 1
-        ;;
-esac
-
-# prepare directory
-rm -fr NATIVE
-mkdir -p "$JSG_BUNDLE"
-
-if [ "$1" = "-so" ]; then
-    shift
-    for file; do
-        [ "$file" != "-txt" ] || break
-        cp -f "$file" "$JSG_BUNDLE"
-        "$STRIP" -S "$JSG_BUNDLE/${file##*/}"
-        shift
-    done
-fi
-
-if [ "$1" = "-txt" ]; then
-    shift
-    for file; do
-        cp -f "$file" "$JSG_BUNDLE"
-        shift
-    done
-fi
similarity index 92%
rename from tools/cmake/AddTests.cmake
rename to tools/cmake/Tests.cmake
index 6e15755..3c5612d 100644 (file)
@@ -59,39 +59,38 @@ MACRO(ADD_TESH_FACTORIES NAME FACTORIES)
   ENDFOREACH()
 ENDMACRO()
 
-INCLUDE(CTest)
-ENABLE_TESTING()
-
 IF(NOT enable_memcheck)
   ## CORE ##
   ### TESH ###
-  ADD_TESH(tesh-self-basic                       --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/basic.tesh)
-  ADD_TESH(tesh-self-cd                          --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/cd.tesh)
-  ADD_TESH(tesh-self-IO-broken-pipe              --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/IO-broken-pipe.tesh)
-  ADD_TESH(tesh-self-IO-orders                   --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/IO-orders.tesh)
-  ADD_TESH(tesh-self-IO-bigsize                  --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/IO-bigsize.tesh)
-  ADD_TESH(tesh-self-set-return                  --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-return.tesh)
-  ADD_TESH(tesh-self-set-timeout                 --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-timeout.tesh)
-  ADD_TESH(tesh-self-set-output-ignore           --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-output-ignore.tesh)
-  ADD_TESH(tesh-self-set-output-sort             --setenv bindir=${CMAKE_BINARY_DIR}/bin --cd "${CMAKE_HOME_DIRECTORY}/tools/tesh" set-output-sort.tesh)
-  ADD_TESH(tesh-self-catch-return                --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-return.tesh)
-  ADD_TESH(tesh-self-catch-timeout               --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-timeout.tesh)
-  ADD_TESH(tesh-self-catch-wrong-output          --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-wrong-output.tesh)
-  ADD_TESH(tesh-self-bg-basic                    --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/bg-basic.tesh)
-  ADD_TESH(tesh-self-background                  --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/background.tesh)
   IF(NOT WIN32)
-    ADD_TESH(tesh-self-set-signal                --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-signal.tesh)
-    ADD_TESH(tesh-self-bg-set-signal             --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/bg-set-signal.tesh)
-    ADD_TESH(tesh-self-catch-signal              --cd "${CMAKE_BINARY_DIR}/bin" ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-signal.tesh)
+    ADD_TESH(tesh-self-basic              --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/basic.tesh)
+    ADD_TESH(tesh-self-cd                 --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/cd.tesh)
+    ADD_TESH(tesh-self-setenv             --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/setenv.tesh)
+    ADD_TESH(tesh-self-IO-broken-pipe     --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/IO-broken-pipe.tesh)
+    ADD_TESH(tesh-self-IO-orders          --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/IO-orders.tesh)
+    ADD_TESH(tesh-self-IO-bigsize         --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/IO-bigsize.tesh)
+    ADD_TESH(tesh-self-set-return         --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-return.tesh)
+    ADD_TESH(tesh-self-set-timeout        --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-timeout.tesh)
+    ADD_TESH(tesh-self-set-output-ignore  --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-output-ignore.tesh)
+    ADD_TESH(tesh-self-set-output-sort    --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/set-output-sort.tesh)
+    ADD_TESH(tesh-self-catch-return       --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-return.tesh)
+    ADD_TESH(tesh-self-catch-timeout      --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-timeout.tesh)
+    ADD_TESH(tesh-self-catch-wrong-output --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-wrong-output.tesh)
+    ADD_TESH(tesh-self-bg-basic           --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/bg-basic.tesh)
+    ADD_TESH(tesh-self-background         --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/background.tesh)
+    ADD_TESH(tesh-self-bg-set-signal      --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/bg-set-signal.tesh)
+    ADD_TESH(tesh-self-catch-signal       --setenv bindir=${CMAKE_BINARY_DIR}/bin ${CMAKE_HOME_DIRECTORY}/tools/tesh/catch-signal.tesh)
   ENDIF()
 
   ### GENERIC  ###
   # BEGIN TESH TESTS
   # test for code coverage
-  ADD_TEST(test-help                             ${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms/basic_parsing_test --help)
-  ADD_TEST(test-help-models                      ${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms/basic_parsing_test --help-models)
-  ADD_TEST(test-tracing-help                   ${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms/basic_parsing_test --help-tracing)
-  ADD_TESH(graphicator                         --setenv srcdir=${CMAKE_HOME_DIRECTORY} --setenv bindir=${CMAKE_BINARY_DIR}/bin --cd ${CMAKE_HOME_DIRECTORY}/tools/graphicator graphicator.tesh)
+  IF(NOT WIN32)
+    ADD_TEST(test-help                             ${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms/basic_parsing_test --help)
+    ADD_TEST(test-help-models                      ${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms/basic_parsing_test --help-models)
+    ADD_TEST(test-tracing-help                   ${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms/basic_parsing_test --help-tracing)
+    ADD_TESH(graphicator                         --setenv srcdir=${CMAKE_HOME_DIRECTORY} --setenv bindir=${CMAKE_BINARY_DIR}/bin --cd ${CMAKE_HOME_DIRECTORY}/tools/graphicator graphicator.tesh)
+  ENDIF()
   # END TESH TESTS
 
   ADD_TESH(mc-replay-random-bug                  --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc/replay --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite/mc/replay --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc/replay random_bug_replay.tesh)
@@ -101,10 +100,10 @@ IF(NOT enable_memcheck)
     ADD_TESH(tesh-mc-dwarf                       --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc/dwarf --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc/dwarf dwarf.tesh)
     ADD_TESH(tesh-mc-dwarf-expression            --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc/dwarf_expression --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc/dwarf_expression dwarf_expression.tesh)
 
-    ADD_TESH(tesh-mc-mutex-handling              --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc mutex_handling.tesh --cfg=model-check/reduction:none)
-    ADD_TESH(tesh-mc-mutex-handling-dpor         --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc mutex_handling.tesh --cfg=model-check/reduction:dpor)
-    ADD_TESH(tesh-mc-no-mutex-handling           --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc no_mutex_handling.tesh --cfg=model-check/reduction:none)
-    ADD_TESH(tesh-mc-no-mutex-handling-dpor      --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc no_mutex_handling.tesh --cfg=model-check/reduction:dpor)
+    ADD_TESH(tesh-mc-with-mutex-handling              --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc with_mutex_handling.tesh --cfg=model-check/reduction:none)
+#    ADD_TESH(tesh-mc-with-mutex-handling-dpor         --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc with_mutex_handling.tesh --cfg=model-check/reduction:dpor)
+    ADD_TESH(tesh-mc-without-mutex-handling           --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc without_mutex_handling.tesh --cfg=model-check/reduction:none)
+    ADD_TESH(tesh-mc-without-mutex-handling-dpor      --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc without_mutex_handling.tesh --cfg=model-check/reduction:dpor)
 
     ADD_TESH(mc-record-random-bug                --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/mc/replay --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite/mc/replay --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/mc/replay random_bug.tesh)
 
@@ -309,7 +308,6 @@ IF(NOT enable_memcheck)
   ADD_TESH(tesh-simdag-flatifier                 --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms --setenv srcdir=${CMAKE_HOME_DIRECTORY} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/simdag/platforms flatifier.tesh)
   ADD_TESH(tesh-simdag-link                      --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms --setenv srcdir=${CMAKE_HOME_DIRECTORY} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/simdag/platforms basic_link_test.tesh)
   ADD_TESH(tesh-simdag-reinit-costs              --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite --cd ${CMAKE_BINARY_DIR}/teshsuite ${CMAKE_HOME_DIRECTORY}/teshsuite/simdag/network/test_reinit_costs.tesh)
-  set_property(TEST tesh-simdag-reinit-costs PROPERTY WILL_FAIL TRUE)
   ADD_TESH(tesh-simdag-parser                    --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/simdag/platforms basic_parsing_test.tesh)
   ADD_TESH(tesh-simdag-parser-sym-full           --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/simdag/platforms basic_parsing_test_sym_full.tesh)
   ADD_TESH(tesh-simdag-full-links                --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/simdag/platforms --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/simdag/platforms get_full_link.tesh)
@@ -510,10 +508,10 @@ IF(NOT enable_memcheck)
   ### JAVA ###
   IF(enable_java)
     IF(WIN32)
-      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/java/\;${CMAKE_BINARY_DIR}/teshsuite/java/\;${SIMGRID_FULL_JAR}")
+      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/java/\;${CMAKE_BINARY_DIR}/teshsuite/java/\;${SIMGRID_JAR}")
       STRING(REPLACE "\;" "§" TESH_CLASSPATH "${TESH_CLASSPATH}")
     ELSE()
-      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/java/:${CMAKE_BINARY_DIR}/teshsuite/java/:${SIMGRID_FULL_JAR}")
+      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/java/:${CMAKE_BINARY_DIR}/teshsuite/java/:${SIMGRID_JAR}")
     ENDIF()
     ADD_TESH(java-async                          --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/async/async.tesh)
     ADD_TESH(java-bittorrent                     --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/bittorrent/bittorrent.tesh)
@@ -529,12 +527,12 @@ IF(NOT enable_memcheck)
     ADD_TESH(java-mutualExclusion                --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/mutualExclusion/mutualexclusion.tesh)
     ADD_TESH(java-pingPong                       --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/pingPong/pingpong.tesh)
     ADD_TESH(java-priority                       --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/priority/priority.tesh)
-    ADD_TESH(java-reservation-surf-plugin        --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/reservationSurfPlugin/reservation_surf_plugin.tesh)
     ADD_TESH(java-startKillTime                  --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/startKillTime/startKillTime.tesh)
     ADD_TESH(java-surf-cpu-model                 --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/surfCpuModel/surf_cpu_model.tesh)
     ADD_TESH(java-surf-plugin                    --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/surfPlugin/surf_plugin.tesh)
+    ADD_TESH(java-surf-plugin-reservation        --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/reservationSurfPlugin/reservation_surf_plugin.tesh)
     ADD_TESH(java-suspend                        --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/suspend/suspend.tesh)
-    ADD_TESH(java-tracing                      --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/tracing/tracingPingPong.tesh)
+    ADD_TESH(java-tracing                        --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/java ${CMAKE_HOME_DIRECTORY}/examples/java/tracing/tracingPingPong.tesh)
 
     # teshsuite ones
     ADD_TESH(tesh-java-sleep-host-off            --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite/java --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/teshsuite/java ${CMAKE_HOME_DIRECTORY}/teshsuite/java/sleep_host_off/sleep_host_off.tesh)
@@ -544,10 +542,10 @@ IF(NOT enable_memcheck)
   ### SCALA ###
   IF(enable_scala)
     IF(WIN32)
-      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/scala/\;${SIMGRID_FULL_JAR}\;${SCALA_JARS}")
+      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/scala/\;${SIMGRID_JAR}\;${SCALA_JARS}")
       STRING(REPLACE "\;" "§" TESH_CLASSPATH "${TESH_CLASSPATH}")
     ELSE()
-      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/scala/:${SIMGRID_FULL_JAR}:${SCALA_JARS}")
+      SET(TESH_CLASSPATH "${CMAKE_BINARY_DIR}/examples/scala/:${SIMGRID_JAR}:${SCALA_JARS}")
     ENDIF()
     ADD_TESH(scala-bypass                        --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/scala --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/scala ${CMAKE_HOME_DIRECTORY}/examples/scala/master_slave_bypass/bypass.tesh)
     ADD_TESH(scala-kill                          --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/scala --setenv classpath=${TESH_CLASSPATH} --cd ${CMAKE_BINARY_DIR}/examples/scala ${CMAKE_HOME_DIRECTORY}/examples/scala/master_slave_kill/kill.tesh)
@@ -556,42 +554,6 @@ IF(NOT enable_memcheck)
 
 ENDIF()
 
-if(enable_smpi AND enable_smpi_ISP_testsuite)
-FOREACH (tesh
-    any_src-can-deadlock10
-    any_src-can-deadlock4
-    any_src-can-deadlock5
-    any_src-can-deadlock6
-    any_src-waitall-deadlock2
-    any_src-waitall-deadlock3
-    any_src-waitany-deadlock2
-    any_src-waitany-deadlock
-    any_src-wait-deadlock
-    basic-deadlock-comm_create
-    basic-deadlock-comm_dup
-    basic-deadlock-comm_split
-    basic-deadlock
-    bcast-deadlock
-    collective-misorder-allreduce
-    collective-misorder
-    complex-deadlock
-    deadlock-config
-    finalize-deadlock
-    irecv-deadlock
-    no-error2
-    no-error3-any_src
-    no-error3
-    no-error
-    )
-  IF(HAVE_MC)
-    ADD_TESH(mc-umpire-${tesh}
-      --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/isp/umpire
-      --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/isp/umpire
-      --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/isp/umpire
-      ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/isp/umpire/${tesh}.tesh)
-  ENDIF()
-ENDFOREACH()
-endif()
 
   ## OTHER ##
 ADD_TEST(testall                                 ${CMAKE_BINARY_DIR}/src/testall)
similarity index 88%
rename from buildtools/Cross/Mingw.cmake
rename to tools/cmake/cross-mingw.cmake
index 14a8165..b82b5c5 100644 (file)
@@ -1,4 +1,4 @@
-# cmake -DCMAKE_TOOLCHAIN_FILE=buildtools/Cross/Mingw.cmake ..
+# cmake -DCMAKE_TOOLCHAIN_FILE=tools/cmake/cross-mingw.cmake ..
 
 set (CMAKE_SYSTEM_NAME Windows)
 set (CMAKE_SYSTEM_PROCESSOR x86_64)
diff --git a/tools/cmake/scripts/IPC/Run.pm b/tools/cmake/scripts/IPC/Run.pm
new file mode 100644 (file)
index 0000000..e2f951e
--- /dev/null
@@ -0,0 +1,4418 @@
+package IPC::Run;
+use bytes;
+
+=pod
+
+=head1 NAME
+
+IPC::Run - system() and background procs w/ piping, redirs, ptys (Unix, Win32)
+
+=head1 SYNOPSIS
+
+   ## First,a command to run:
+      my @cat = qw( cat );
+
+   ## Using run() instead of system():
+      use IPC::Run qw( run timeout );
+
+      run \@cmd, \$in, \$out, \$err, timeout( 10 ) or die "cat: $?"
+
+      # Can do I/O to sub refs and filenames, too:
+      run \@cmd, '<', "in.txt", \&out, \&err or die "cat: $?"
+      run \@cat, '<', "in.txt", '>>', "out.txt", '2>>', "err.txt";
+
+
+      # Redirecting using psuedo-terminals instad of pipes.
+      run \@cat, '<pty<', \$in,  '>pty>', \$out_and_err;
+
+   ## Scripting subprocesses (like Expect):
+
+      use IPC::Run qw( start pump finish timeout );
+
+      # Incrementally read from / write to scalars. 
+      # $in is drained as it is fed to cat's stdin,
+      # $out accumulates cat's stdout
+      # $err accumulates cat's stderr
+      # $h is for "harness".
+      my $h = start \@cat, \$in, \$out, \$err, timeout( 10 );
+
+      $in .= "some input\n";
+      pump $h until $out =~ /input\n/g;
+
+      $in .= "some more input\n";
+      pump $h until $out =~ /\G.*more input\n/;
+
+      $in .= "some final input\n";
+      finish $h or die "cat returned $?";
+
+      warn $err if $err; 
+      print $out;         ## All of cat's output
+
+   # Piping between children
+      run \@cat, '|', \@gzip;
+
+   # Multiple children simultaneously (run() blocks until all
+   # children exit, use start() for background execution):
+      run \@foo1, '&', \@foo2;
+
+   # Calling \&set_up_child in the child before it executes the
+   # command (only works on systems with true fork() & exec())
+   # exceptions thrown in set_up_child() will be propagated back
+   # to the parent and thrown from run().
+      run \@cat, \$in, \$out,
+         init => \&set_up_child;
+
+   # Read from / write to file handles you open and close
+      open IN,  '<in.txt'  or die $!;
+      open OUT, '>out.txt' or die $!;
+      print OUT "preamble\n";
+      run \@cat, \*IN, \*OUT or die "cat returned $?";
+      print OUT "postamble\n";
+      close IN;
+      close OUT;
+
+   # Create pipes for you to read / write (like IPC::Open2 & 3).
+      $h = start
+         \@cat,
+            '<pipe', \*IN,
+            '>pipe', \*OUT,
+            '2>pipe', \*ERR 
+         or die "cat returned $?";
+      print IN "some input\n";
+      close IN;
+      print <OUT>, <ERR>;
+      finish $h;
+
+   # Mixing input and output modes
+      run \@cat, 'in.txt', \&catch_some_out, \*ERR_LOG );
+
+   # Other redirection constructs
+      run \@cat, '>&', \$out_and_err;
+      run \@cat, '2>&1';
+      run \@cat, '0<&3';
+      run \@cat, '<&-';
+      run \@cat, '3<', \$in3;
+      run \@cat, '4>', \$out4;
+      # etc.
+
+   # Passing options:
+      run \@cat, 'in.txt', debug => 1;
+
+   # Call this system's shell, returns TRUE on 0 exit code
+   # THIS IS THE OPPOSITE SENSE OF system()'s RETURN VALUE
+      run "cat a b c" or die "cat returned $?";
+
+   # Launch a sub process directly, no shell.  Can't do redirection
+   # with this form, it's here to behave like system() with an
+   # inverted result.
+      $r = run "cat a b c";
+
+   # Read from a file in to a scalar
+      run io( "filename", 'r', \$recv );
+      run io( \*HANDLE,   'r', \$recv );
+
+=head1 DESCRIPTION
+
+IPC::Run allows you to run and interact with child processes using files, pipes,
+and pseudo-ttys.  Both system()-style and scripted usages are supported and
+may be mixed.  Likewise, functional and OO API styles are both supported and
+may be mixed.
+
+Various redirection operators reminiscent of those seen on common Unix and DOS
+command lines are provided.
+
+Before digging in to the details a few LIMITATIONS are important enough
+to be mentioned right up front:
+
+=over
+
+=item Win32 Support
+
+Win32 support is working but B<EXPERIMENTAL>, but does pass all relevant tests
+on NT 4.0.  See L</Win32 LIMITATIONS>.
+
+=item pty Support
+
+If you need pty support, IPC::Run should work well enough most of the
+time, but IO::Pty is being improved, and IPC::Run will be improved to
+use IO::Pty's new features when it is release.
+
+The basic problem is that the pty needs to initialize itself before the
+parent writes to the master pty, or the data written gets lost.  So
+IPC::Run does a sleep(1) in the parent after forking to (hopefully) give
+the child a chance to run.  This is a kludge that works well on non
+heavily loaded systems :(.
+
+ptys are not supported yet under Win32, but will be emulated...
+
+=item Debugging Tip
+
+You may use the environment variable C<IPCRUNDEBUG> to see what's going on
+under the hood:
+
+   $ IPCRUNDEBUG=basic   myscript     # prints minimal debugging
+   $ IPCRUNDEBUG=data    myscript     # prints all data reads/writes
+   $ IPCRUNDEBUG=details myscript     # prints lots of low-level details
+   $ IPCRUNDEBUG=gory    myscript     # (Win32 only) prints data moving through
+                                      # the helper processes.
+
+=back
+
+We now return you to your regularly scheduled documentation.
+
+=head2 Harnesses
+
+Child processes and I/O handles are gathered in to a harness, then
+started and run until the processing is finished or aborted.
+
+=head2 run() vs. start(); pump(); finish();
+
+There are two modes you can run harnesses in: run() functions as an
+enhanced system(), and start()/pump()/finish() allow for background
+processes and scripted interactions with them.
+
+When using run(), all data to be sent to the harness is set up in
+advance (though one can feed subprocesses input from subroutine refs to
+get around this limitation). The harness is run and all output is
+collected from it, then any child processes are waited for:
+
+   run \@cmd, \<<IN, \$out;
+   blah
+   IN
+
+   ## To precompile harnesses and run them later:
+   my $h = harness \@cmd, \<<IN, \$out;
+   blah
+   IN
+
+   run $h;
+
+The background and scripting API is provided by start(), pump(), and
+finish(): start() creates a harness if need be (by calling harness())
+and launches any subprocesses, pump() allows you to poll them for
+activity, and finish() then monitors the harnessed activities until they
+complete.
+
+   ## Build the harness, open all pipes, and launch the subprocesses
+   my $h = start \@cat, \$in, \$out;
+   $in = "first input\n";
+
+   ## Now do I/O.  start() does no I/O.
+   pump $h while length $in;  ## Wait for all input to go
+
+   ## Now do some more I/O.
+   $in = "second input\n";
+   pump $h until $out =~ /second input/;
+
+   ## Clean up
+   finish $h or die "cat returned $?";
+
+You can optionally compile the harness with harness() prior to
+start()ing or run()ing, and you may omit start() between harness() and
+pump().  You might want to do these things if you compile your harnesses
+ahead of time.
+
+=head2 Using regexps to match output
+
+As shown in most of the scripting examples, the read-to-scalar facility
+for gathering subcommand's output is often used with regular expressions
+to detect stopping points.  This is because subcommand output often
+arrives in dribbles and drabs, often only a character or line at a time.
+This output is input for the main program and piles up in variables like
+the C<$out> and C<$err> in our examples.
+
+Regular expressions can be used to wait for appropriate output in
+several ways.  The C<cat> example in the previous section demonstrates
+how to pump() until some string appears in the output.  Here's an
+example that uses C<smb> to fetch files from a remote server:
+
+   $h = harness \@smbclient, \$in, \$out;
+
+   $in = "cd /src\n";
+   $h->pump until $out =~ /^smb.*> \Z/m;
+   die "error cding to /src:\n$out" if $out =~ "ERR";
+   $out = '';
+
+   $in = "mget *\n";
+   $h->pump until $out =~ /^smb.*> \Z/m;
+   die "error retrieving files:\n$out" if $out =~ "ERR";
+
+   $in = "quit\n";
+   $h->finish;
+
+Notice that we carefully clear $out after the first command/response
+cycle? That's because IPC::Run does not delete $out when we continue,
+and we don't want to trip over the old output in the second
+command/response cycle.
+
+Say you want to accumulate all the output in $out and analyze it
+afterwards.  Perl offers incremental regular expression matching using
+the C<m//gc> and pattern matching idiom and the C<\G> assertion.
+IPC::Run is careful not to disturb the current C<pos()> value for
+scalars it appends data to, so we could modify the above so as not to
+destroy $out by adding a couple of C</gc> modifiers.  The C</g> keeps us
+from tripping over the previous prompt and the C</c> keeps us from
+resetting the prior match position if the expected prompt doesn't
+materialize immediately:
+
+   $h = harness \@smbclient, \$in, \$out;
+
+   $in = "cd /src\n";
+   $h->pump until $out =~ /^smb.*> \Z/mgc;
+   die "error cding to /src:\n$out" if $out =~ "ERR";
+
+   $in = "mget *\n";
+   $h->pump until $out =~ /^smb.*> \Z/mgc;
+   die "error retrieving files:\n$out" if $out =~ "ERR";
+
+   $in = "quit\n";
+   $h->finish;
+
+   analyze( $out );
+
+When using this technique, you may want to preallocate $out to have
+plenty of memory or you may find that the act of growing $out each time
+new input arrives causes an C<O(length($out)^2)> slowdown as $out grows.
+Say we expect no more than 10,000 characters of input at the most.  To
+preallocate memory to $out, do something like:
+
+   my $out = "x" x 10_000;
+   $out = "";
+
+C<perl> will allocate at least 10,000 characters' worth of space, then
+mark the $out as having 0 length without freeing all that yummy RAM.
+
+=head2 Timeouts and Timers
+
+More than likely, you don't want your subprocesses to run forever, and
+sometimes it's nice to know that they're going a little slowly.
+Timeouts throw exceptions after a some time has elapsed, timers merely
+cause pump() to return after some time has elapsed.  Neither is
+reset/restarted automatically.
+
+Timeout objects are created by calling timeout( $interval ) and passing
+the result to run(), start() or harness().  The timeout period starts
+ticking just after all the child processes have been fork()ed or
+spawn()ed, and are polled for expiration in run(), pump() and finish().
+If/when they expire, an exception is thrown.  This is typically useful
+to keep a subprocess from taking too long.
+
+If a timeout occurs in run(), all child processes will be terminated and
+all file/pipe/ptty descriptors opened by run() will be closed.  File
+descriptors opened by the parent process and passed in to run() are not
+closed in this event.
+
+If a timeout occurs in pump(), pump_nb(), or finish(), it's up to you to
+decide whether to kill_kill() all the children or to implement some more
+graceful fallback.  No I/O will be closed in pump(), pump_nb() or
+finish() by such an exception (though I/O is often closed down in those
+routines during the natural course of events).
+
+Often an exception is too harsh.  timer( $interval ) creates timer
+objects that merely prevent pump() from blocking forever.  This can be
+useful for detecting stalled I/O or printing a soothing message or "."
+to pacify an anxious user.
+
+Timeouts and timers can both be restarted at any time using the timer's
+start() method (this is not the start() that launches subprocesses).  To
+restart a timer, you need to keep a reference to the timer:
+
+   ## Start with a nice long timeout to let smbclient connect.  If
+   ## pump or finish take too long, an exception will be thrown.
+
+ my $h;
+ eval {
+   $h = harness \@smbclient, \$in, \$out, \$err, ( my $t = timeout 30 );
+   sleep 11;  # No effect: timer not running yet
+
+   start $h;
+   $in = "cd /src\n";
+   pump $h until ! length $in;
+
+   $in = "ls\n";
+   ## Now use a short timeout, since this should be faster
+   $t->start( 5 );
+   pump $h until ! length $in;
+
+   $t->start( 10 );  ## Give smbclient a little while to shut down.
+   $h->finish;
+ };
+ if ( $@ ) {
+   my $x = $@;    ## Preserve $@ in case another exception occurs
+   $h->kill_kill; ## kill it gently, then brutally if need be, or just
+                   ## brutally on Win32.
+   die $x;
+ }
+
+Timeouts and timers are I<not> checked once the subprocesses are shut
+down; they will not expire in the interval between the last valid
+process and when IPC::Run scoops up the processes' result codes, for
+instance.
+
+=head2 Spawning synchronization, child exception propagation
+
+start() pauses the parent until the child executes the command or CODE
+reference and propagates any exceptions thrown (including exec()
+failure) back to the parent.  This has several pleasant effects: any
+exceptions thrown in the child, including exec() failure, come flying
+out of start() or run() as though they had occurred in the parent.
+
+This includes exceptions your code thrown from init subs.  In this
+example:
+
+   eval {
+      run \@cmd, init => sub { die "blast it! foiled again!" };
+   };
+   print $@;
+
+the exception "blast it! foiled again" will be thrown from the child
+process (preventing the exec()) and printed by the parent.
+
+In situations like
+
+   run \@cmd1, "|", \@cmd2, "|", \@cmd3;
+
+@cmd1 will be initted and exec()ed before @cmd2, and @cmd2 before @cmd3.
+This can save time and prevent oddball errors emitted by later commands
+when earlier commands fail to execute.  Note that IPC::Run doesn't start
+any commands unless it can find the executables referenced by all
+commands.  These executables must pass both the C<-f> and C<-x> tests
+described in L<perlfunc>.
+
+Another nice effect is that init() subs can take their time doing things
+and there will be no problems caused by a parent continuing to execute
+before a child's init() routine is complete.  Say the init() routine
+needs to open a socket or a temp file that the parent wants to connect
+to; without this synchronization, the parent will need to implement a
+retry loop to wait for the child to run, since often, the parent gets a
+lot of things done before the child's first timeslice is allocated.
+
+This is also quite necessary for pseudo-tty initialization, which needs
+to take place before the parent writes to the child via pty.  Writes
+that occur before the pty is set up can get lost.
+
+A final, minor, nicety is that debugging output from the child will be
+emitted before the parent continues on, making for much clearer debugging
+output in complex situations.
+
+The only drawback I can conceive of is that the parent can't continue to
+operate while the child is being initted.  If this ever becomes a
+problem in the field, we can implement an option to avoid this behavior,
+but I don't expect it to.
+
+B<Win32>: executing CODE references isn't supported on Win32, see
+L</Win32 LIMITATIONS> for details.
+
+=head2 Syntax
+
+run(), start(), and harness() can all take a harness specification
+as input.  A harness specification is either a single string to be passed
+to the systems' shell:
+
+   run "echo 'hi there'";
+
+or a list of commands, io operations, and/or timers/timeouts to execute.
+Consecutive commands must be separated by a pipe operator '|' or an '&'.
+External commands are passed in as array references, and, on systems
+supporting fork(), Perl code may be passed in as subs:
+
+   run \@cmd;
+   run \@cmd1, '|', \@cmd2;
+   run \@cmd1, '&', \@cmd2;
+   run \&sub1;
+   run \&sub1, '|', \&sub2;
+   run \&sub1, '&', \&sub2;
+
+'|' pipes the stdout of \@cmd1 the stdin of \@cmd2, just like a
+shell pipe.  '&' does not.  Child processes to the right of a '&'
+will have their stdin closed unless it's redirected-to.
+
+L<IPC::Run::IO> objects may be passed in as well, whether or not
+child processes are also specified:
+
+   run io( "infile", ">", \$in ), io( "outfile", "<", \$in );
+      
+as can L<IPC::Run::Timer> objects:
+
+   run \@cmd, io( "outfile", "<", \$in ), timeout( 10 );
+
+Commands may be followed by scalar, sub, or i/o handle references for
+redirecting
+child process input & output:
+
+   run \@cmd,  \undef,            \$out;
+   run \@cmd,  \$in,              \$out;
+   run \@cmd1, \&in, '|', \@cmd2, \*OUT;
+   run \@cmd1, \*IN, '|', \@cmd2, \&out;
+
+This is known as succinct redirection syntax, since run(), start()
+and harness(), figure out which file descriptor to redirect and how.
+File descriptor 0 is presumed to be an input for
+the child process, all others are outputs.  The assumed file
+descriptor always starts at 0, unless the command is being piped to,
+in which case it starts at 1.
+
+To be explicit about your redirects, or if you need to do more complex
+things, there's also a redirection operator syntax:
+
+   run \@cmd, '<', \undef, '>',  \$out;
+   run \@cmd, '<', \undef, '>&', \$out_and_err;
+   run(
+      \@cmd1,
+         '<', \$in,
+      '|', \@cmd2,
+         \$out
+   );
+
+Operator syntax is required if you need to do something other than simple
+redirection to/from scalars or subs, like duping or closing file descriptors
+or redirecting to/from a named file.  The operators are covered in detail
+below.
+
+After each \@cmd (or \&foo), parsing begins in succinct mode and toggles to
+operator syntax mode when an operator (ie plain scalar, not a ref) is seen.
+Once in
+operator syntax mode, parsing only reverts to succinct mode when a '|' or
+'&' is seen.
+
+In succinct mode, each parameter after the \@cmd specifies what to
+do with the next highest file descriptor. These File descriptor start
+with 0 (stdin) unless stdin is being piped to (C<'|', \@cmd>), in which
+case they start with 1 (stdout).  Currently, being on the left of
+a pipe (C<\@cmd, \$out, \$err, '|'>) does I<not> cause stdout to be
+skipped, though this may change since it's not as DWIMerly as it
+could be.  Only stdin is assumed to be an
+input in succinct mode, all others are assumed to be outputs.
+
+If no piping or redirection is specified for a child, it will inherit
+the parent's open file handles as dictated by your system's
+close-on-exec behavior and the $^F flag, except that processes after a
+'&' will not inherit the parent's stdin. Also note that $^F does not
+affect file descriptors obtained via POSIX, since it only applies to
+full-fledged Perl file handles.  Such processes will have their stdin
+closed unless it has been redirected-to.
+
+If you want to close a child processes stdin, you may do any of:
+
+   run \@cmd, \undef;
+   run \@cmd, \"";
+   run \@cmd, '<&-';
+   run \@cmd, '0<&-';
+
+Redirection is done by placing redirection specifications immediately 
+after a command or child subroutine:
+
+   run \@cmd1,      \$in, '|', \@cmd2,      \$out;
+   run \@cmd1, '<', \$in, '|', \@cmd2, '>', \$out;
+
+If you omit the redirection operators, descriptors are counted
+starting at 0.  Descriptor 0 is assumed to be input, all others
+are outputs.  A leading '|' consumes descriptor 0, so this
+works as expected.
+
+   run \@cmd1, \$in, '|', \@cmd2, \$out;
+   
+The parameter following a redirection operator can be a scalar ref,
+a subroutine ref, a file name, an open filehandle, or a closed
+filehandle.
+
+If it's a scalar ref, the child reads input from or sends output to
+that variable:
+
+   $in = "Hello World.\n";
+   run \@cat, \$in, \$out;
+   print $out;
+
+Scalars used in incremental (start()/pump()/finish()) applications are treated
+as queues: input is removed from input scalers, resulting in them dwindling
+to '', and output is appended to output scalars.  This is not true of 
+harnesses run() in batch mode.
+
+It's usually wise to append new input to be sent to the child to the input
+queue, and you'll often want to zap output queues to '' before pumping.
+
+   $h = start \@cat, \$in;
+   $in = "line 1\n";
+   pump $h;
+   $in .= "line 2\n";
+   pump $h;
+   $in .= "line 3\n";
+   finish $h;
+
+The final call to finish() must be there: it allows the child process(es)
+to run to completion and waits for their exit values.
+
+=head1 OBSTINATE CHILDREN
+
+Interactive applications are usually optimized for human use.  This
+can help or hinder trying to interact with them through modules like
+IPC::Run.  Frequently, programs alter their behavior when they detect
+that stdin, stdout, or stderr are not connected to a tty, assuming that
+they are being run in batch mode.  Whether this helps or hurts depends
+on which optimizations change.  And there's often no way of telling
+what a program does in these areas other than trial and error and,
+occasionally, reading the source.  This includes different versions
+and implementations of the same program.
+
+All hope is not lost, however.  Most programs behave in reasonably
+tractable manners, once you figure out what it's trying to do.
+
+Here are some of the issues you might need to be aware of.
+
+=over
+
+=item *
+
+fflush()ing stdout and stderr
+
+This lets the user see stdout and stderr immediately.  Many programs
+undo this optimization if stdout is not a tty, making them harder to
+manage by things like IPC::Run.
+
+Many programs decline to fflush stdout or stderr if they do not
+detect a tty there.  Some ftp commands do this, for instance.
+
+If this happens to you, look for a way to force interactive behavior,
+like a command line switch or command.  If you can't, you will
+need to use a pseudo terminal ('<pty<' and '>pty>').
+
+=item *
+
+false prompts
+
+Interactive programs generally do not guarantee that output from user
+commands won't contain a prompt string.  For example, your shell prompt
+might be a '$', and a file named '$' might be the only file in a directory
+listing.
+
+This can make it hard to guarantee that your output parser won't be fooled
+into early termination of results.
+
+To help work around this, you can see if the program can alter it's 
+prompt, and use something you feel is never going to occur in actual
+practice.
+
+You should also look for your prompt to be the only thing on a line:
+
+   pump $h until $out =~ /^<SILLYPROMPT>\s?\z/m;
+
+(use C<(?!\n)\Z> in place of C<\z> on older perls).
+
+You can also take the approach that IPC::ChildSafe takes and emit a
+command with known output after each 'real' command you issue, then
+look for this known output.  See new_appender() and new_chunker() for
+filters that can help with this task.
+
+If it's not convenient or possibly to alter a prompt or use a known
+command/response pair, you might need to autodetect the prompt in case
+the local version of the child program is different then the one
+you tested with, or if the user has control over the look & feel of
+the prompt.
+
+=item *
+
+Refusing to accept input unless stdin is a tty.
+
+Some programs, for security reasons, will only accept certain types
+of input from a tty.  su, notable, will not prompt for a password unless
+it's connected to a tty.
+
+If this is your situation, use a pseudo terminal ('<pty<' and '>pty>').
+
+=item *
+
+Not prompting unless connected to a tty.
+
+Some programs don't prompt unless stdin or stdout is a tty.  See if you can
+turn prompting back on.  If not, see if you can come up with a command that
+you can issue after every real command and look for it's output, as
+IPC::ChildSafe does.   There are two filters included with IPC::Run that
+can help with doing this: appender and chunker (see new_appender() and
+new_chunker()).
+
+=item *
+
+Different output format when not connected to a tty.
+
+Some commands alter their formats to ease machine parsability when they
+aren't connected to a pipe.  This is actually good, but can be surprising.
+
+=back
+
+=head1 PSEUDO TERMINALS
+
+On systems providing pseudo terminals under /dev, IPC::Run can use IO::Pty
+(available on CPAN) to provide a terminal environment to subprocesses.
+This is necessary when the subprocess really wants to think it's connected
+to a real terminal.
+
+=head2 CAVEATS
+
+Psuedo-terminals are not pipes, though they are similar.  Here are some
+differences to watch out for.
+
+=over
+
+=item Echoing
+
+Sending to stdin will cause an echo on stdout, which occurs before each
+line is passed to the child program.  There is currently no way to
+disable this, although the child process can and should disable it for
+things like passwords.
+
+=item Shutdown
+
+IPC::Run cannot close a pty until all output has been collected.  This
+means that it is not possible to send an EOF to stdin by half-closing
+the pty, as we can when using a pipe to stdin.
+
+This means that you need to send the child process an exit command or
+signal, or run() / finish() will time out.  Be careful not to expect a
+prompt after sending the exit command.
+
+=item Command line editing
+
+Some subprocesses, notable shells that depend on the user's prompt
+settings, will reissue the prompt plus the command line input so far
+once for each character.
+
+=item '>pty>' means '&>pty>', not '1>pty>'
+
+The pseudo terminal redirects both stdout and stderr unless you specify
+a file descriptor.  If you want to grab stderr separately, do this:
+
+   start \@cmd, '<pty<', \$in, '>pty>', \$out, '2>', \$err;
+
+=item stdin, stdout, and stderr not inherited
+
+Child processes harnessed to a pseudo terminal have their stdin, stdout,
+and stderr completely closed before any redirection operators take
+effect.  This casts of the bonds of the controlling terminal.  This is
+not done when using pipes.
+
+Right now, this affects all children in a harness that has a pty in use,
+even if that pty would not affect a particular child.  That's a bug and
+will be fixed.  Until it is, it's best not to mix-and-match children.
+
+=back
+
+=head2 Redirection Operators
+
+   Operator       SHNP   Description
+   ========       ====   ===========
+   <, N<          SHN    Redirects input to a child's fd N (0 assumed)
+
+   >, N>          SHN    Redirects output from a child's fd N (1 assumed)
+   >>, N>>        SHN    Like '>', but appends to scalars or named files
+   >&, &>         SHN    Redirects stdout & stderr from a child process
+
+   <pty, N<pty    S      Like '<', but uses a pseudo-tty instead of a pipe
+   >pty, N>pty    S      Like '>', but uses a pseudo-tty instead of a pipe
+
+   N<&M                  Dups input fd N to input fd M
+   M>&N                  Dups output fd N to input fd M
+   N<&-                  Closes fd N
+
+   <pipe, N<pipe     P   Pipe opens H for caller to read, write, close.
+   >pipe, N>pipe     P   Pipe opens H for caller to read, write, close.
+                      
+'N' and 'M' are placeholders for integer file descriptor numbers.  The
+terms 'input' and 'output' are from the child process's perspective.
+
+The SHNP field indicates what parameters an operator can take:
+
+   S: \$scalar or \&function references.  Filters may be used with
+      these operators (and only these).
+   H: \*HANDLE or IO::Handle for caller to open, and close
+   N: "file name".
+   P: \*HANDLE opened by IPC::Run as the parent end of a pipe, but read
+      and written to and closed by the caller (like IPC::Open3).
+
+=over
+
+=item Redirecting input: [n]<, [n]<pipe
+
+You can input the child reads on file descriptor number n to come from a
+scalar variable, subroutine, file handle, or a named file.  If stdin
+is not redirected, the parent's stdin is inherited.
+
+   run \@cat, \undef          ## Closes child's stdin immediately
+      or die "cat returned $?"; 
+
+   run \@cat, \$in;
+
+   run \@cat, \<<TOHERE;
+   blah
+   TOHERE
+
+   run \@cat, \&input;       ## Calls &input, feeding data returned
+                              ## to child's.  Closes child's stdin
+                              ## when undef is returned.
+
+Redirecting from named files requires you to use the input
+redirection operator:
+
+   run \@cat, '<.profile';
+   run \@cat, '<', '.profile';
+
+   open IN, "<foo";
+   run \@cat, \*IN;
+   run \@cat, *IN{IO};
+
+The form used second example here is the safest,
+since filenames like "0" and "&more\n" won't confuse &run:
+
+You can't do either of
+
+   run \@a, *IN;      ## INVALID
+   run \@a, '<', *IN; ## BUGGY: Reads file named like "*main::A"
+   
+because perl passes a scalar containing a string that
+looks like "*main::A" to &run, and &run can't tell the difference
+between that and a redirection operator or a file name.  &run guarantees
+that any scalar you pass after a redirection operator is a file name.
+
+If your child process will take input from file descriptors other
+than 0 (stdin), you can use a redirection operator with any of the
+valid input forms (scalar ref, sub ref, etc.):
+
+   run \@cat, '3<', \$in3;
+
+When redirecting input from a scalar ref, the scalar ref is
+used as a queue.  This allows you to use &harness and pump() to
+feed incremental bits of input to a coprocess.  See L</Coprocesses>
+below for more information.
+
+The <pipe operator opens the write half of a pipe on the filehandle
+glob reference it takes as an argument:
+
+   $h = start \@cat, '<pipe', \*IN;
+   print IN "hello world\n";
+   pump $h;
+   close IN;
+   finish $h;
+
+Unlike the other '<' operators, IPC::Run does nothing further with
+it: you are responsible for it.  The previous example is functionally
+equivalent to:
+
+   pipe( \*R, \*IN ) or die $!;
+   $h = start \@cat, '<', \*IN;
+   print IN "hello world\n";
+   pump $h;
+   close IN;
+   finish $h;
+
+This is like the behavior of IPC::Open2 and IPC::Open3.
+
+B<Win32>: The handle returned is actually a socket handle, so you can
+use select() on it.
+
+=item Redirecting output: [n]>, [n]>>, [n]>&[m], [n]>pipe
+
+You can redirect any output the child emits
+to a scalar variable, subroutine, file handle, or file name.  You
+can have &run truncate or append to named files or scalars.  If
+you are redirecting stdin as well, or if the command is on the
+receiving end of a pipeline ('|'), you can omit the redirection
+operator:
+
+   @ls = ( 'ls' );
+   run \@ls, \undef, \$out
+      or die "ls returned $?"; 
+
+   run \@ls, \undef, \&out;  ## Calls &out each time some output
+                              ## is received from the child's 
+                              ## when undef is returned.
+
+   run \@ls, \undef, '2>ls.err';
+   run \@ls, '2>', 'ls.err';
+
+The two parameter form guarantees that the filename
+will not be interpreted as a redirection operator:
+
+   run \@ls, '>', "&more";
+   run \@ls, '2>', ">foo\n";
+
+You can pass file handles you've opened for writing:
+
+   open( *OUT, ">out.txt" );
+   open( *ERR, ">err.txt" );
+   run \@cat, \*OUT, \*ERR;
+
+Passing a scalar reference and a code reference requires a little
+more work, but allows you to capture all of the output in a scalar
+or each piece of output by a callback:
+
+These two do the same things:
+
+   run( [ 'ls' ], '2>', sub { $err_out .= $_[0] } );
+
+does the same basic thing as:
+
+   run( [ 'ls' ], '2>', \$err_out );
+
+The subroutine will be called each time some data is read from the child.
+
+The >pipe operator is different in concept than the other '>' operators,
+although it's syntax is similar:
+
+   $h = start \@cat, $in, '>pipe', \*OUT, '2>pipe', \*ERR;
+   $in = "hello world\n";
+   finish $h;
+   print <OUT>;
+   print <ERR>;
+   close OUT;
+   close ERR;
+
+causes two pipe to be created, with one end attached to cat's stdout
+and stderr, respectively, and the other left open on OUT and ERR, so
+that the script can manually
+read(), select(), etc. on them.  This is like
+the behavior of IPC::Open2 and IPC::Open3.
+
+B<Win32>: The handle returned is actually a socket handle, so you can
+use select() on it.
+
+=item Duplicating output descriptors: >&m, n>&m
+
+This duplicates output descriptor number n (default is 1 if n is omitted)
+from descriptor number m.
+
+=item Duplicating input descriptors: <&m, n<&m
+
+This duplicates input descriptor number n (default is 0 if n is omitted)
+from descriptor number m
+
+=item Closing descriptors: <&-, 3<&-
+
+This closes descriptor number n (default is 0 if n is omitted).  The
+following commands are equivalent:
+
+   run \@cmd, \undef;
+   run \@cmd, '<&-';
+   run \@cmd, '<in.txt', '<&-';
+
+Doing
+
+   run \@cmd, \$in, '<&-';    ## SIGPIPE recipe.
+
+is dangerous: the parent will get a SIGPIPE if $in is not empty.
+
+=item Redirecting both stdout and stderr: &>, >&, &>pipe, >pipe&
+
+The following pairs of commands are equivalent:
+
+   run \@cmd, '>&', \$out;       run \@cmd, '>', \$out,     '2>&1';
+   run \@cmd, '>&', 'out.txt';   run \@cmd, '>', 'out.txt', '2>&1';
+
+etc.
+
+File descriptor numbers are not permitted to the left or the right of
+these operators, and the '&' may occur on either end of the operator.
+
+The '&>pipe' and '>pipe&' variants behave like the '>pipe' operator, except
+that both stdout and stderr write to the created pipe.
+
+=item Redirection Filters
+
+Both input redirections and output redirections that use scalars or
+subs as endpoints may have an arbitrary number of filter subs placed
+between them and the child process.  This is useful if you want to
+receive output in chunks, or if you want to massage each chunk of
+data sent to the child.  To use this feature, you must use operator
+syntax:
+
+   run(
+      \@cmd
+         '<', \&in_filter_2, \&in_filter_1, $in,
+         '>', \&out_filter_1, \&in_filter_2, $out,
+   );
+
+This capability is not provided for IO handles or named files.
+
+Two filters are provided by IPC::Run: appender and chunker.  Because
+these may take an argument, you need to use the constructor functions
+new_appender() and new_chunker() rather than using \& syntax:
+
+   run(
+      \@cmd
+         '<', new_appender( "\n" ), $in,
+         '>', new_chunker, $out,
+   );
+
+=back
+
+=head2 Just doing I/O
+
+If you just want to do I/O to a handle or file you open yourself, you
+may specify a filehandle or filename instead of a command in the harness
+specification:
+
+   run io( "filename", '>', \$recv );
+
+   $h = start io( $io, '>', \$recv );
+
+   $h = harness \@cmd, '&', io( "file", '<', \$send );
+
+=head2 Options
+
+Options are passed in as name/value pairs:
+
+   run \@cat, \$in, debug => 1;
+
+If you pass the debug option, you may want to pass it in first, so you
+can see what parsing is going on:
+
+   run debug => 1, \@cat, \$in;
+
+=over
+
+=item debug
+
+Enables debugging output in parent and child.  Debugging info is emitted
+to the STDERR that was present when IPC::Run was first C<use()>ed (it's
+C<dup()>ed out of the way so that it can be redirected in children without
+having debugging output emitted on it).
+
+=back
+
+=head1 RETURN VALUES
+
+harness() and start() return a reference to an IPC::Run harness.  This is
+blessed in to the IPC::Run package, so you may make later calls to
+functions as members if you like:
+
+   $h = harness( ... );
+   $h->start;
+   $h->pump;
+   $h->finish;
+
+   $h = start( .... );
+   $h->pump;
+   ...
+
+Of course, using method call syntax lets you deal with any IPC::Run
+subclasses that might crop up, but don't hold your breath waiting for
+any.
+
+run() and finish() return TRUE when all subcommands exit with a 0 result
+code.  B<This is the opposite of perl's system() command>.
+
+All routines raise exceptions (via die()) when error conditions are
+recognized.  A non-zero command result is not treated as an error
+condition, since some commands are tests whose results are reported 
+in their exit codes.
+
+=head1 ROUTINES
+
+=over
+
+=cut
+
+use strict;
+use Exporter ();
+use vars qw{$VERSION @ISA @FILTER_IMP @FILTERS @API @EXPORT_OK %EXPORT_TAGS};
+BEGIN {
+       $VERSION = '0.94';
+       @ISA     = qw{ Exporter };
+
+       ## We use @EXPORT for the end user's convenience: there's only one function
+       ## exported, it's homonymous with the module, it's an unusual name, and
+       ## it can be suppressed by "use IPC::Run ();".
+       @FILTER_IMP = qw( input_avail get_more_input );
+       @FILTERS    = qw(
+               new_appender
+               new_chunker
+               new_string_source
+               new_string_sink
+       );
+       @API        = qw(
+               run
+               harness start pump pumpable finish
+               signal kill_kill reap_nb
+               io timer timeout
+               close_terminal
+               binary
+       );
+       @EXPORT_OK = ( @API, @FILTER_IMP, @FILTERS, qw( Win32_MODE ) );
+       %EXPORT_TAGS = (
+               'filter_imp' => \@FILTER_IMP,
+               'all'        => \@EXPORT_OK,
+               'filters'    => \@FILTERS,
+               'api'        => \@API,
+       );
+
+}
+
+use strict;
+use IPC::Run::Debug;
+use Exporter;
+use Fcntl;
+use POSIX ();
+BEGIN { if ($] < 5.008) { require Symbol; } }
+use Carp;
+use File::Spec ();
+use IO::Handle;
+require IPC::Run::IO;
+require IPC::Run::Timer;
+use UNIVERSAL ();
+
+use constant Win32_MODE => $^O =~ /os2|Win32/i;
+
+BEGIN {
+   if ( Win32_MODE ) {
+      eval "use IPC::Run::Win32Helper; 1;"
+         or ( $@ && die ) or die "$!";
+   }
+   else {
+      eval "use File::Basename; 1;" or die $!;
+   }
+}
+
+sub input_avail();
+sub get_more_input();
+
+###############################################################################
+
+##
+## Error constants, not too locale-dependant
+use vars  qw( $_EIO $_EAGAIN );
+use Errno qw(   EIO   EAGAIN );
+BEGIN {
+  local $!;
+  $! = EIO;    $_EIO    = qr/^$!/;
+  $! = EAGAIN; $_EAGAIN = qr/^$!/;
+}
+
+##
+## State machine states, set in $self->{STATE}
+##
+## These must be in ascending order numerically
+##
+sub _newed()    {0}
+sub _harnessed(){1}
+sub _finished() {2}   ## _finished behave almost exactly like _harnessed
+sub _started()  {3}
+
+##
+## Which fds have been opened in the parent.  This may have extra fds, since
+## we aren't all that rigorous about closing these off, but that's ok.  This
+## is used on Unixish OSs to close all fds in the child that aren't needed
+## by that particular child.
+my %fds;
+
+## There's a bit of hackery going on here.
+##
+## We want to have any code anywhere be able to emit
+## debugging statements without knowing what harness the code is
+## being called in/from, since we'd need to pass a harness around to
+## everything.
+##
+## Thus, $cur_self was born.
+
+use vars qw( $cur_self );
+
+sub _debug_fd {
+   return fileno STDERR unless defined $cur_self;
+
+   if ( _debugging && ! defined $cur_self->{DEBUG_FD} ) {
+      my $fd = select STDERR; $| = 1; select $fd;
+      $cur_self->{DEBUG_FD} = POSIX::dup fileno STDERR;
+      _debug( "debugging fd is $cur_self->{DEBUG_FD}\n" )
+         if _debugging_details;
+   }
+
+   return fileno STDERR unless defined $cur_self->{DEBUG_FD};
+
+   return $cur_self->{DEBUG_FD}
+}
+
+sub DESTROY {
+   ## We absolutely do not want to do anything else here.  We are likely
+   ## to be in a child process and we don't want to do things like kill_kill
+   ## ourself or cause other destruction.
+   my IPC::Run $self = shift;
+   POSIX::close $self->{DEBUG_FD} if defined $self->{DEBUG_FD};
+   $self->{DEBUG_FD} = undef;
+}
+
+##
+## Support routines (NOT METHODS)
+##
+my %cmd_cache;
+
+sub _search_path {
+   my ( $cmd_name ) = @_;
+   if ( File::Spec->file_name_is_absolute( $cmd_name ) && -x $cmd_name) {
+      _debug "'", $cmd_name, "' is absolute"
+         if _debugging_details;
+      return $cmd_name;
+   }
+
+   my $dirsep =
+      ( Win32_MODE
+         ? '[/\\\\]'
+      : $^O =~ /MacOS/
+         ? ':'
+      : $^O =~ /VMS/
+         ? '[\[\]]'
+      : '/'
+      );
+
+   if ( Win32_MODE
+      && ( $cmd_name =~ /$dirsep/ )
+#      && ( $cmd_name !~ /\..+$/ )  ## Only run if cmd_name has no extension?
+      && ( $cmd_name !~ m!\.[^\\/\.]+$! )
+    ) {
+
+      _debug "no extension(.exe), checking ENV{PATHEXT}"  if _debugging;
+      for ( split /;/, $ENV{PATHEXT} || ".COM;.BAT;.EXE" ) {
+         my $name = "$cmd_name$_";
+         $cmd_name = $name, last if -f $name && -x _;
+      }
+      _debug "cmd_name is now '$cmd_name'"  if _debugging;
+   }
+
+   if ( $cmd_name =~ /($dirsep)/ ) {
+      _debug "'$cmd_name' contains '$1'"  if _debugging;
+      croak "file not found: $cmd_name"    unless -e $cmd_name;
+      croak "not a file: $cmd_name"        unless -f $cmd_name;
+      croak "permission denied: $cmd_name" unless -x $cmd_name;
+      return $cmd_name;
+   }
+
+   if ( exists $cmd_cache{$cmd_name} ) {
+      _debug "'$cmd_name' found in cache: '$cmd_cache{$cmd_name}'"
+         if _debugging;
+      return $cmd_cache{$cmd_name} if -x $cmd_cache{$cmd_name};
+      _debug "'$cmd_cache{$cmd_name}' no longer executable, searching..."
+         if _debugging;
+      delete $cmd_cache{$cmd_name};
+   }
+
+   my @searched_in;
+
+   ## This next bit is Unix/Win32 specific, unfortunately.
+   ## There's been some conversation about extending File::Spec to provide
+   ## a universal interface to PATH, but I haven't seen it yet.
+      my $re = Win32_MODE ? qr/;/ : qr/:/;
+
+LOOP:
+   for ( split( $re, $ENV{PATH} || '', -1 ) ) {
+      $_ = "." unless length $_;
+      push @searched_in, $_;
+
+      my $prospect = File::Spec->catfile( $_, $cmd_name );
+      my @prospects;
+
+      @prospects =
+         ( Win32_MODE && ! ( -f $prospect && -x _ ) )
+            ? map "$prospect$_", split /;/, $ENV{PATHEXT} || ".COM;.BAT;.EXE"
+            : ( $prospect );
+
+      for my $found ( @prospects ) {
+         if ( -f $found && -x _ ) {
+            $cmd_cache{$cmd_name} = $found;
+            last LOOP;
+         }
+      }
+   }
+
+   if ( exists $cmd_cache{$cmd_name} ) {
+      _debug "'", $cmd_name, "' added to cache: '", $cmd_cache{$cmd_name}, "'"
+         if _debugging_details;
+      return $cmd_cache{$cmd_name};
+   }
+
+   croak "Command '$cmd_name' not found in " . join( ", ", @searched_in );
+}
+
+
+sub _empty($) { ! ( defined $_[0] && length $_[0] ) }
+
+## 'safe' versions of otherwise fun things to do. See also IPC::Run::Win32Helper.
+sub _close {
+   confess 'undef' unless defined $_[0];
+   my $fd = $_[0] =~ /^\d+$/ ? $_[0] : fileno $_[0];
+   my $r = POSIX::close $fd;
+   $r = $r ? '' : " ERROR $!";
+   delete $fds{$fd};
+   _debug "close( $fd ) = " . ( $r || 0 ) if _debugging_details;
+}
+
+sub _dup {
+   confess 'undef' unless defined $_[0];
+   my $r = POSIX::dup( $_[0] );
+   croak "$!: dup( $_[0] )" unless defined $r;
+   $r = 0 if $r eq '0 but true';
+   _debug "dup( $_[0] ) = $r" if _debugging_details;
+   $fds{$r} = 1;
+   return $r;
+}
+
+
+sub _dup2_rudely {
+   confess 'undef' unless defined $_[0] && defined $_[1];
+   my $r = POSIX::dup2( $_[0], $_[1] );
+   croak "$!: dup2( $_[0], $_[1] )" unless defined $r;
+   $r = 0 if $r eq '0 but true';
+   _debug "dup2( $_[0], $_[1] ) = $r" if _debugging_details;
+   $fds{$r} = 1;
+   return $r;
+}
+
+sub _exec {
+   confess 'undef passed' if grep !defined, @_;
+#   exec @_ or croak "$!: exec( " . join( ', ', @_ ) . " )";
+   _debug 'exec()ing ', join " ", map "'$_'", @_ if _debugging_details;
+
+#   {
+## Commented out since we don't call this on Win32.
+#      # This works around the bug where 5.6.1 complains
+#      # "Can't exec ...: No error" after an exec on NT, where
+#      # exec() is simulated and actually returns in Perl's C
+#      # code, though Perl's &exec does not...
+#      no warnings "exec";
+#
+#      # Just in case the no warnings workaround
+#      # stops being a workaround, we don't want
+#      # old values of $! causing spurious strerr()
+#      # messages to appear in the "Can't exec" message
+#      undef $!;
+      exec { $_[0] } @_;
+#   }
+#   croak "$!: exec( " . join( ', ', map "'$_'", @_ ) . " )";
+    ## Fall through so $! can be reported to parent.
+}
+
+
+sub _sysopen {
+   confess 'undef' unless defined $_[0] && defined $_[1];
+_debug sprintf( "O_RDONLY=0x%02x ", O_RDONLY ),
+sprintf( "O_WRONLY=0x%02x ", O_WRONLY ),
+sprintf( "O_RDWR=0x%02x ", O_RDWR ),
+sprintf( "O_TRUNC=0x%02x ", O_TRUNC),
+sprintf( "O_CREAT=0x%02x ", O_CREAT),
+sprintf( "O_APPEND=0x%02x ", O_APPEND),
+if _debugging_details;
+   my $r = POSIX::open( $_[0], $_[1], 0644 );
+   croak "$!: open( $_[0], ", sprintf( "0x%03x", $_[1] ), " )" unless defined $r;
+   _debug "open( $_[0], ", sprintf( "0x%03x", $_[1] ), " ) = $r"
+      if _debugging_data;
+   $fds{$r} = 1;
+   return $r;
+}
+
+sub _pipe {
+   ## Normal, blocking write for pipes that we read and the child writes,
+   ## since most children expect writes to stdout to block rather than
+   ## do a partial write.
+   my ( $r, $w ) = POSIX::pipe;
+   croak "$!: pipe()" unless defined $r;
+   _debug "pipe() = ( $r, $w ) " if _debugging_details;
+   $fds{$r} = $fds{$w} = 1;
+   return ( $r, $w );
+}
+
+sub _pipe_nb {
+   ## For pipes that we write, unblock the write side, so we can fill a buffer
+   ## and continue to select().
+   ## Contributed by Borislav Deianov <borislav@ensim.com>, with minor
+   ## bugfix on fcntl result by me.
+   local ( *R, *W );
+   my $f = pipe( R, W );
+   croak "$!: pipe()" unless defined $f;
+   my ( $r, $w ) = ( fileno R, fileno W );
+   _debug "pipe_nb pipe() = ( $r, $w )" if _debugging_details;
+   unless ( Win32_MODE ) {
+      ## POSIX::fcntl doesn't take fd numbers, so gotta use Perl's and
+      ## then _dup the originals (which get closed on leaving this block)
+      my $fres = fcntl( W, &F_SETFL, O_WRONLY | O_NONBLOCK );
+      croak "$!: fcntl( $w, F_SETFL, O_NONBLOCK )" unless $fres;
+      _debug "fcntl( $w, F_SETFL, O_NONBLOCK )" if _debugging_details;
+   }
+   ( $r, $w ) = ( _dup( $r ), _dup( $w ) );
+   _debug "pipe_nb() = ( $r, $w )" if _debugging_details;
+   return ( $r, $w );
+}
+
+sub _pty {
+   require IO::Pty;
+   my $pty = IO::Pty->new();
+   croak "$!: pty ()" unless $pty;
+   $pty->autoflush();
+   $pty->blocking( 0 ) or croak "$!: pty->blocking ( 0 )";
+   _debug "pty() = ( ", $pty->fileno, ", ", $pty->slave->fileno, " )"
+      if _debugging_details;
+   $fds{$pty->fileno} = $fds{$pty->slave->fileno} = 1;
+   return $pty;
+}
+
+
+sub _read {
+   confess 'undef' unless defined $_[0];
+   my $s  = '';
+   my $r = POSIX::read( $_[0], $s, 10_000 );
+   croak "$!: read( $_[0] )" if not($r) and $! != POSIX::EINTR;
+   $r ||= 0;
+   _debug "read( $_[0] ) = $r chars '$s'" if _debugging_data;
+   return $s;
+}
+
+
+## A METHOD, not a function.
+sub _spawn {
+   my IPC::Run $self = shift;
+   my ( $kid ) = @_;
+
+   _debug "opening sync pipe ", $kid->{PID} if _debugging_details;
+   my $sync_reader_fd;
+   ( $sync_reader_fd, $self->{SYNC_WRITER_FD} ) = _pipe;
+   $kid->{PID} = fork();
+   croak "$! during fork" unless defined $kid->{PID};
+
+   unless ( $kid->{PID} ) {
+      ## _do_kid_and_exit closes sync_reader_fd since it closes all unwanted and
+      ## unloved fds.
+      $self->_do_kid_and_exit( $kid );
+   }
+   _debug "fork() = ", $kid->{PID} if _debugging_details;
+
+   ## Wait for kid to get to it's exec() and see if it fails.
+   _close $self->{SYNC_WRITER_FD};
+   my $sync_pulse = _read $sync_reader_fd;
+   _close $sync_reader_fd;
+
+   if ( ! defined $sync_pulse || length $sync_pulse ) {
+      if ( waitpid( $kid->{PID}, 0 ) >= 0 ) {
+        $kid->{RESULT} = $?;
+      }
+      else {
+        $kid->{RESULT} = -1;
+      }
+      $sync_pulse =
+         "error reading synchronization pipe for $kid->{NUM}, pid $kid->{PID}"
+        unless length $sync_pulse;
+      croak $sync_pulse;
+   }
+   return $kid->{PID};
+
+## Wait for pty to get set up.  This is a hack until we get synchronous
+## selects.
+if ( keys %{$self->{PTYS}} && $IO::Pty::VERSION < 0.9 ) {
+_debug "sleeping to give pty a chance to init, will fix when newer IO::Pty arrives.";
+sleep 1;
+}
+}
+
+
+sub _write {
+   confess 'undef' unless defined $_[0] && defined $_[1];
+   my $r = POSIX::write( $_[0], $_[1], length $_[1] );
+   croak "$!: write( $_[0], '$_[1]' )" unless $r;
+   _debug "write( $_[0], '$_[1]' ) = $r" if _debugging_data;
+   return $r;
+}
+
+=pod
+
+=over
+
+=item run
+
+Run takes a harness or harness specification and runs it, pumping
+all input to the child(ren), closing the input pipes when no more
+input is available, collecting all output that arrives, until the
+pipes delivering output are closed, then waiting for the children to
+exit and reaping their result codes.
+
+You may think of C<run( ... )> as being like 
+
+   start( ... )->finish();
+
+, though there is one subtle difference: run() does not
+set \$input_scalars to '' like finish() does.  If an exception is thrown
+from run(), all children will be killed off "gently", and then "annihilated"
+if they do not go gently (in to that dark night. sorry).
+
+If any exceptions are thrown, this does a L</kill_kill> before propagating
+them.
+
+=cut
+
+use vars qw( $in_run );  ## No, not Enron;)
+
+sub run {
+   local $in_run = 1;  ## Allow run()-only optimizations.
+   my IPC::Run $self = start( @_ );
+   my $r = eval {
+      $self->{clear_ins} = 0;
+      $self->finish;
+   };
+   if ( $@ ) {
+      my $x = $@;
+      $self->kill_kill;
+      die $x;
+   }
+   return $r;
+}
+
+=pod
+
+=item signal
+
+   ## To send it a specific signal by name ("USR1"):
+   signal $h, "USR1";
+   $h->signal ( "USR1" );
+
+If $signal is provided and defined, sends a signal to all child processes.  Try
+not to send numeric signals, use C<"KILL"> instead of C<9>, for instance.
+Numeric signals aren't portable.
+
+Throws an exception if $signal is undef.
+
+This will I<not> clean up the harness, C<finish> it if you kill it.
+
+Normally TERM kills a process gracefully (this is what the command line utility
+C<kill> does by default), INT is sent by one of the keys C<^C>, C<Backspace> or
+C<E<lt>DelE<gt>>, and C<QUIT> is used to kill a process and make it coredump.
+
+The C<HUP> signal is often used to get a process to "restart", rereading 
+config files, and C<USR1> and C<USR2> for really application-specific things.
+
+Often, running C<kill -l> (that's a lower case "L") on the command line will
+list the signals present on your operating system.
+
+B<WARNING>: The signal subsystem is not at all portable.  We *may* offer
+to simulate C<TERM> and C<KILL> on some operating systems, submit code
+to me if you want this.
+
+B<WARNING 2>: Up to and including perl v5.6.1, doing almost anything in a
+signal handler could be dangerous.  The most safe code avoids all
+mallocs and system calls, usually by preallocating a flag before
+entering the signal handler, altering the flag's value in the
+handler, and responding to the changed value in the main system:
+
+   my $got_usr1 = 0;
+   sub usr1_handler { ++$got_signal }
+
+   $SIG{USR1} = \&usr1_handler;
+   while () { sleep 1; print "GOT IT" while $got_usr1--; }
+
+Even this approach is perilous if ++ and -- aren't atomic on your system
+(I've never heard of this on any modern CPU large enough to run perl).
+
+=cut
+
+sub signal {
+   my IPC::Run $self = shift;
+
+   local $cur_self = $self;
+
+   $self->_kill_kill_kill_pussycat_kill unless @_;
+
+   Carp::cluck "Ignoring extra parameters passed to kill()" if @_ > 1;
+
+   my ( $signal ) = @_;
+   croak "Undefined signal passed to signal" unless defined $signal;
+   for ( grep $_->{PID} && ! defined $_->{RESULT}, @{$self->{KIDS}} ) {
+      _debug "sending $signal to $_->{PID}"
+         if _debugging;
+      kill $signal, $_->{PID}
+         or _debugging && _debug "$! sending $signal to $_->{PID}";
+   }
+   
+   return;
+}
+
+=pod
+
+=item kill_kill
+
+   ## To kill off a process:
+   $h->kill_kill;
+   kill_kill $h;
+
+   ## To specify the grace period other than 30 seconds:
+   kill_kill $h, grace => 5;
+
+   ## To send QUIT instead of KILL if a process refuses to die:
+   kill_kill $h, coup_d_grace => "QUIT";
+
+Sends a C<TERM>, waits for all children to exit for up to 30 seconds, then
+sends a C<KILL> to any that survived the C<TERM>.
+
+Will wait for up to 30 more seconds for the OS to successfully C<KILL> the
+processes.
+
+The 30 seconds may be overridden by setting the C<grace> option, this
+overrides both timers.
+
+The harness is then cleaned up.
+
+The doubled name indicates that this function may kill again and avoids
+colliding with the core Perl C<kill> function.
+
+Returns a 1 if the C<TERM> was sufficient, or a 0 if C<KILL> was 
+required.  Throws an exception if C<KILL> did not permit the children
+to be reaped.
+
+B<NOTE>: The grace period is actually up to 1 second longer than that
+given.  This is because the granularity of C<time> is 1 second.  Let me
+know if you need finer granularity, we can leverage Time::HiRes here.
+
+B<Win32>: Win32 does not know how to send real signals, so C<TERM> is
+a full-force kill on Win32.  Thus all talk of grace periods, etc. do
+not apply to Win32.
+
+=cut
+
+sub kill_kill {
+   my IPC::Run $self = shift;
+
+   my %options = @_;
+   my $grace = $options{grace};
+   $grace = 30 unless defined $grace;
+   ++$grace; ## Make grace time a _minimum_
+
+   my $coup_d_grace = $options{coup_d_grace};
+   $coup_d_grace = "KILL" unless defined $coup_d_grace;
+
+   delete $options{$_} for qw( grace coup_d_grace );
+   Carp::cluck "Ignoring unknown options for kill_kill: ",
+       join " ",keys %options
+       if keys %options;
+
+   $self->signal( "TERM" );
+
+   my $quitting_time = time + $grace;
+   my $delay = 0.01;
+   my $accum_delay;
+
+   my $have_killed_before;
+
+   while () {
+      ## delay first to yield to other processes
+      select undef, undef, undef, $delay;
+      $accum_delay += $delay;
+
+      $self->reap_nb;
+      last unless $self->_running_kids;
+
+      if ( $accum_delay >= $grace*0.8 ) {
+         ## No point in checking until delay has grown some.
+         if ( time >= $quitting_time ) {
+            if ( ! $have_killed_before ) {
+               $self->signal( $coup_d_grace );
+               $have_killed_before = 1;
+               $quitting_time += $grace;
+               $delay = 0.01;
+               $accum_delay = 0;
+               next;
+            }
+            croak "Unable to reap all children, even after KILLing them"
+         }
+      }
+
+      $delay *= 2;
+      $delay = 0.5 if $delay >= 0.5;
+   }
+
+   $self->_cleanup;
+   return $have_killed_before;
+}
+
+=pod
+
+=item harness
+
+Takes a harness specification and returns a harness.  This harness is
+blessed in to IPC::Run, allowing you to use method call syntax for
+run(), start(), et al if you like.
+
+harness() is provided so that you can pre-build harnesses if you
+would like to, but it's not required..
+
+You may proceed to run(), start() or pump() after calling harness() (pump()
+calls start() if need be).  Alternatively, you may pass your
+harness specification to run() or start() and let them harness() for
+you.  You can't pass harness specifications to pump(), though.
+
+=cut
+
+##
+## Notes: I've avoided handling a scalar that doesn't look like an
+## opcode as a here document or as a filename, though I could DWIM
+## those.  I'm not sure that the advantages outweigh the danger when
+## the DWIMer guesses wrong.
+##
+## TODO: allow user to spec default shell. Hmm, globally, in the
+## lexical scope hash, or per instance?  'Course they can do that
+## now by using a [...] to hold the command.
+##
+my $harness_id = 0;
+sub harness {
+   my $options;
+   if ( @_ && ref $_[-1] eq 'HASH' ) {
+      $options = pop;
+      require Data::Dumper;
+      carp "Passing in options as a hash is deprecated:\n", Data::Dumper::Dumper( $options );
+   }
+
+#   local $IPC::Run::debug = $options->{debug}
+#      if $options && defined $options->{debug};
+
+   my @args;
+   if ( @_ == 1 && ! ref $_[0] ) {
+      if ( Win32_MODE ) {
+         my $command = $ENV{ComSpec} || 'cmd';
+         @args = ( [ $command, '/c', win32_parse_cmd_line $_[0] ] );
+      }
+      else {
+         @args = ( [ qw( sh -c ), @_ ] );
+      }
+   }
+   elsif ( @_ > 1 && ! grep ref $_, @_ ) {
+      @args = ( [ @_ ] );
+   }
+   else {
+      @args = @_;
+   }
+
+   my @errs;               # Accum errors, emit them when done.
+
+   my $succinct;           # set if no redir ops are required yet.  Cleared
+                            # if an op is seen.
+
+   my $cur_kid;            # references kid or handle being parsed
+
+   my $assumed_fd    = 0;  # fd to assume in succinct mode (no redir ops)
+   my $handle_num    = 0;  # 1... is which handle we're parsing
+
+   my IPC::Run $self = bless {}, __PACKAGE__;
+
+   local $cur_self = $self;
+
+   $self->{ID}    = ++$harness_id;
+   $self->{IOS}   = [];
+   $self->{KIDS}  = [];
+   $self->{PIPES} = [];
+   $self->{PTYS}  = {};
+   $self->{STATE} = _newed;
+
+   if ( $options ) {
+      $self->{$_} = $options->{$_}
+         for keys %$options;
+   }
+
+   _debug "****** harnessing *****" if _debugging;
+
+   my $first_parse;
+   local $_;
+   my $arg_count = @args;
+   while ( @args ) { for ( shift @args ) {
+      eval {
+         $first_parse = 1;
+         _debug(
+            "parsing ",
+            defined $_
+               ? ref $_ eq 'ARRAY'
+                  ? ( '[ ', join( ', ', map "'$_'", @$_ ), ' ]' )
+                  : ( ref $_
+                     || ( length $_ < 50
+                           ? "'$_'"
+                           : join( '', "'", substr( $_, 0, 10 ), "...'" )
+                        )
+                  )
+               : '<undef>'
+         ) if _debugging;
+
+      REPARSE:
+         if ( ref eq 'ARRAY' || ( ! $cur_kid && ref eq 'CODE' ) ) {
+            croak "Process control symbol ('|', '&') missing" if $cur_kid;
+            croak "Can't spawn a subroutine on Win32"
+              if Win32_MODE && ref eq "CODE";
+            $cur_kid = {
+               TYPE   => 'cmd',
+               VAL    => $_,
+               NUM    => @{$self->{KIDS}} + 1,
+               OPS    => [],
+               PID    => '',
+               RESULT => undef,
+            };
+            push @{$self->{KIDS}}, $cur_kid;
+            $succinct = 1;
+         }
+
+         elsif ( UNIVERSAL::isa( $_, 'IPC::Run::IO' ) ) {
+            push @{$self->{IOS}}, $_;
+            $cur_kid = undef;
+            $succinct = 1;
+         }
+         
+         elsif ( UNIVERSAL::isa( $_, 'IPC::Run::Timer' ) ) {
+            push @{$self->{TIMERS}}, $_;
+            $cur_kid = undef;
+            $succinct = 1;
+         }
+         
+         elsif ( /^(\d*)>&(\d+)$/ ) {
+            croak "No command before '$_'" unless $cur_kid;
+            push @{$cur_kid->{OPS}}, {
+               TYPE => 'dup',
+               KFD1 => $2,
+               KFD2 => length $1 ? $1 : 1,
+            };
+            _debug "redirect operators now required" if _debugging_details;
+            $succinct = ! $first_parse;
+         }
+
+         elsif ( /^(\d*)<&(\d+)$/ ) {
+            croak "No command before '$_'" unless $cur_kid;
+            push @{$cur_kid->{OPS}}, {
+               TYPE => 'dup',
+               KFD1 => $2,
+               KFD2 => length $1 ? $1 : 0,
+            };
+            $succinct = ! $first_parse;
+         }
+
+         elsif ( /^(\d*)<&-$/ ) {
+            croak "No command before '$_'" unless $cur_kid;
+            push @{$cur_kid->{OPS}}, {
+               TYPE => 'close',
+               KFD  => length $1 ? $1 : 0,
+            };
+            $succinct = ! $first_parse;
+         }
+
+         elsif (
+               /^(\d*) (<pipe)()            ()  ()  $/x
+            || /^(\d*) (<pty) ((?:\s+\S+)?) (<) ()  $/x
+            || /^(\d*) (<)    ()            ()  (.*)$/x
+         ) {
+            croak "No command before '$_'" unless $cur_kid;
+
+            $succinct = ! $first_parse;
+
+            my $type = $2 . $4;
+
+            my $kfd = length $1 ? $1 : 0;
+
+            my $pty_id;
+            if ( $type eq '<pty<' ) {
+               $pty_id = length $3 ? $3 : '0';
+               ## do the require here to cause early error reporting
+               require IO::Pty;
+               ## Just flag the pyt's existence for now.  It'll be
+               ## converted to a real IO::Pty by _open_pipes.
+               $self->{PTYS}->{$pty_id} = undef;
+            }
+
+            my $source = $5;
+
+            my @filters;
+            my $binmode;
+
+            unless ( length $source ) {
+               if ( ! $succinct ) {
+                  while ( @args > 1
+                      && (
+                         ( ref $args[1] && ! UNIVERSAL::isa $args[1], "IPC::Run::Timer" )
+                         || UNIVERSAL::isa $args[0], "IPC::Run::binmode_pseudo_filter"
+                      )
+                  ) {
+                     if ( UNIVERSAL::isa $args[0], "IPC::Run::binmode_pseudo_filter" ) {
+                        $binmode = shift( @args )->();
+                     }
+                     else {
+                        push @filters, shift @args
+                     }
+                  }
+               }
+               $source = shift @args;
+               croak "'$_' missing a source" if _empty $source;
+
+               _debug(
+                  'Kid ', $cur_kid->{NUM}, "'s input fd ", $kfd,
+                  ' has ', scalar( @filters ), ' filters.'
+               ) if _debugging_details && @filters;
+            };
+
+            my IPC::Run::IO $pipe = IPC::Run::IO->_new_internal(
+               $type, $kfd, $pty_id, $source, $binmode, @filters
+            );
+
+            if ( ( ref $source eq 'GLOB' || UNIVERSAL::isa $source, 'IO::Handle' )
+               && $type !~ /^<p(ty<|ipe)$/
+            ) {
+              _debug "setting DONT_CLOSE" if _debugging_details;
+               $pipe->{DONT_CLOSE} = 1; ## this FD is not closed by us.
+              _dont_inherit( $source ) if Win32_MODE;
+            }
+
+            push @{$cur_kid->{OPS}}, $pipe;
+      }
+
+         elsif ( /^()   (>>?)  (&)     ()      (.*)$/x
+            ||   /^()   (&)    (>pipe) ()      ()  $/x 
+            ||   /^()   (>pipe)(&)     ()      ()  $/x 
+            ||   /^(\d*)()     (>pipe) ()      ()  $/x
+            ||   /^()   (&)    (>pty)  ( \w*)> ()  $/x 
+## TODO:    ||   /^()   (>pty) (\d*)> (&) ()  $/x 
+            ||   /^(\d*)()     (>pty)  ( \w*)> ()  $/x
+            ||   /^()   (&)    (>>?)   ()      (.*)$/x 
+            ||   /^(\d*)()     (>>?)   ()      (.*)$/x
+         ) {
+            croak "No command before '$_'" unless $cur_kid;
+
+            $succinct = ! $first_parse;
+
+            my $type = (
+               $2 eq '>pipe' || $3 eq '>pipe'
+                  ? '>pipe'
+                  : $2 eq '>pty' || $3 eq '>pty'
+                     ? '>pty>'
+                     : '>'
+            );
+            my $kfd = length $1 ? $1 : 1;
+            my $trunc = ! ( $2 eq '>>' || $3 eq '>>' );
+            my $pty_id = (
+               $2 eq '>pty' || $3 eq '>pty'
+                  ? length $4 ? $4 : 0
+                  : undef
+            );
+
+            my $stderr_too =
+                  $2 eq '&'
+               || $3 eq '&'
+               || ( ! length $1 && substr( $type, 0, 4 ) eq '>pty' );
+
+            my $dest = $5;
+            my @filters;
+            my $binmode = 0;
+            unless ( length $dest ) {
+               if ( ! $succinct ) {
+                  ## unshift...shift: '>' filters source...sink left...right
+                  while ( @args > 1
+                     && ( 
+                        ( ref $args[1] && !  UNIVERSAL::isa $args[1], "IPC::Run::Timer" )
+                        || UNIVERSAL::isa $args[0], "IPC::Run::binmode_pseudo_filter"
+                     )
+                  ) {
+                     if ( UNIVERSAL::isa $args[0], "IPC::Run::binmode_pseudo_filter" ) {
+                        $binmode = shift( @args )->();
+                     }
+                     else {
+                        unshift @filters, shift @args;
+                     }
+                  }
+               }
+
+               $dest = shift @args;
+
+               _debug(
+                  'Kid ', $cur_kid->{NUM}, "'s output fd ", $kfd,
+                  ' has ', scalar( @filters ), ' filters.'
+               ) if _debugging_details && @filters;
+
+               if ( $type eq '>pty>' ) {
+                  ## do the require here to cause early error reporting
+                  require IO::Pty;
+                  ## Just flag the pyt's existence for now.  _open_pipes()
+                  ## will new an IO::Pty for each key.
+                  $self->{PTYS}->{$pty_id} = undef;
+               }
+            }
+
+            croak "'$_' missing a destination" if _empty $dest;
+            my $pipe = IPC::Run::IO->_new_internal(
+               $type, $kfd, $pty_id, $dest, $binmode, @filters
+            );
+            $pipe->{TRUNC} = $trunc;
+
+            if (  ( UNIVERSAL::isa( $dest, 'GLOB' ) || UNIVERSAL::isa( $dest, 'IO::Handle' ) )
+               && $type !~ /^>(pty>|pipe)$/
+            ) {
+              _debug "setting DONT_CLOSE" if _debugging_details;
+               $pipe->{DONT_CLOSE} = 1; ## this FD is not closed by us.
+            }
+            push @{$cur_kid->{OPS}}, $pipe;
+            push @{$cur_kid->{OPS}}, {
+               TYPE => 'dup',
+               KFD1 => 1,
+               KFD2 => 2,
+            } if $stderr_too;
+         }
+
+         elsif ( $_ eq "|" ) {
+            croak "No command before '$_'" unless $cur_kid;
+            unshift @{$cur_kid->{OPS}}, {
+               TYPE => '|',
+               KFD  => 1,
+            };
+            $succinct   = 1;
+            $assumed_fd = 1;
+            $cur_kid    = undef;
+         }
+
+         elsif ( $_ eq "&" ) {
+            croak "No command before '$_'" unless $cur_kid;
+            unshift @{$cur_kid->{OPS}}, {
+               TYPE => 'close',
+               KFD  => 0,
+            };
+            $succinct   = 1;
+            $assumed_fd = 0;
+            $cur_kid    = undef;
+         }
+
+         elsif ( $_ eq 'init' ) {
+            croak "No command before '$_'" unless $cur_kid;
+            push @{$cur_kid->{OPS}}, {
+               TYPE => 'init',
+               SUB  => shift @args,
+            };
+         }
+
+         elsif ( ! ref $_ ) {
+            $self->{$_} = shift @args;
+         }
+
+         elsif ( $_ eq 'init' ) {
+            croak "No command before '$_'" unless $cur_kid;
+            push @{$cur_kid->{OPS}}, {
+               TYPE => 'init',
+               SUB  => shift @args,
+            };
+         }
+
+         elsif ( $succinct && $first_parse ) {
+            ## It's not an opcode, and no explicit opcodes have been
+            ## seen yet, so assume it's a file name.
+            unshift @args, $_;
+            if ( ! $assumed_fd ) {
+               $_ = "$assumed_fd<",
+            }
+            else {
+               $_ = "$assumed_fd>",
+            }
+            _debug "assuming '", $_, "'" if _debugging_details;
+            ++$assumed_fd;
+            $first_parse = 0;
+            goto REPARSE;
+         }
+
+         else {
+            croak join( 
+               '',
+               'Unexpected ',
+               ( ref() ? $_ : 'scalar' ),
+               ' in harness() parameter ',
+               $arg_count - @args
+            );
+         }
+      };
+      if ( $@ ) {
+         push @errs, $@;
+         _debug 'caught ', $@ if _debugging;
+      }
+   } }
+
+   die join( '', @errs ) if @errs;
+
+
+   $self->{STATE} = _harnessed;
+#   $self->timeout( $options->{timeout} ) if exists $options->{timeout};
+   return $self;
+}
+
+
+sub _open_pipes {
+   my IPC::Run $self = shift;
+
+   my @errs;
+
+   my @close_on_fail;
+
+   ## When a pipe character is seen, a pipe is created.  $pipe_read_fd holds
+   ## the dangling read end of the pipe until we get to the next process.
+   my $pipe_read_fd;
+
+   ## Output descriptors for the last command are shared by all children.
+   ## @output_fds_accum accumulates the current set of output fds.
+   my @output_fds_accum;
+
+   for ( sort keys %{$self->{PTYS}} ) {
+      _debug "opening pty '", $_, "'" if _debugging_details;
+      my $pty = _pty;
+      $self->{PTYS}->{$_} = $pty;
+   }
+
+   for ( @{$self->{IOS}} ) {
+      eval { $_->init; };
+      if ( $@ ) {
+         push @errs, $@;
+         _debug 'caught ', $@ if _debugging;
+      }
+      else {
+         push @close_on_fail, $_;
+      }
+   }
+
+   ## Loop through the kids and their OPS, interpreting any that require
+   ## parent-side actions.
+   for my $kid ( @{$self->{KIDS}} ) {
+      unless ( ref $kid->{VAL} eq 'CODE' ) {
+         $kid->{PATH} = _search_path $kid->{VAL}->[0];
+      }
+      if ( defined $pipe_read_fd ) {
+        _debug "placing write end of pipe on kid $kid->{NUM}'s stdin"
+           if _debugging_details;
+         unshift @{$kid->{OPS}}, {
+            TYPE => 'PIPE',  ## Prevent next loop from triggering on this
+            KFD  => 0,
+            TFD  => $pipe_read_fd,
+         };
+         $pipe_read_fd = undef;
+      }
+      @output_fds_accum = ();
+      for my $op ( @{$kid->{OPS}} ) {
+#         next if $op->{IS_DEBUG};
+         my $ok = eval {
+            if ( $op->{TYPE} eq '<' ) {
+               my $source = $op->{SOURCE};
+              if ( ! ref $source ) {
+                 _debug(
+                    "kid ", $kid->{NUM}, " to read ", $op->{KFD},
+                    " from '" .  $source, "' (read only)"
+                 ) if _debugging_details;
+                 croak "simulated open failure"
+                    if $self->{_simulate_open_failure};
+                 $op->{TFD} = _sysopen( $source, O_RDONLY );
+                 push @close_on_fail, $op->{TFD};
+              }
+              elsif ( UNIVERSAL::isa( $source, 'GLOB' )
+                 ||   UNIVERSAL::isa( $source, 'IO::Handle' )
+              ) {
+                 croak
+                    "Unopened filehandle in input redirect for $op->{KFD}"
+                    unless defined fileno $source;
+                 $op->{TFD} = fileno $source;
+                 _debug(
+                    "kid ", $kid->{NUM}, " to read ", $op->{KFD},
+                    " from fd ", $op->{TFD}
+                 ) if _debugging_details;
+              }
+              elsif ( UNIVERSAL::isa( $source, 'SCALAR' ) ) {
+                 _debug(
+                    "kid ", $kid->{NUM}, " to read ", $op->{KFD},
+                    " from SCALAR"
+                 ) if _debugging_details;
+
+                 $op->open_pipe( $self->_debug_fd );
+                 push @close_on_fail, $op->{KFD}, $op->{FD};
+
+                 my $s = '';
+                 $op->{KIN_REF} = \$s;
+              }
+              elsif ( UNIVERSAL::isa( $source, 'CODE' ) ) {
+                 _debug(
+                    'kid ', $kid->{NUM}, ' to read ', $op->{KFD}, ' from CODE'
+                 ) if _debugging_details;
+                 
+                 $op->open_pipe( $self->_debug_fd );
+                 push @close_on_fail, $op->{KFD}, $op->{FD};
+                 
+                 my $s = '';
+                 $op->{KIN_REF} = \$s;
+              }
+              else {
+                 croak(
+                    "'"
+                    . ref( $source )
+                    . "' not allowed as a source for input redirection"
+                 );
+              }
+               $op->_init_filters;
+            }
+            elsif ( $op->{TYPE} eq '<pipe' ) {
+               _debug(
+                  'kid to read ', $op->{KFD},
+                  ' from a pipe IPC::Run opens and returns',
+               ) if _debugging_details;
+
+               my ( $r, $w ) = $op->open_pipe( $self->_debug_fd, $op->{SOURCE} );
+              _debug "caller will write to ", fileno $op->{SOURCE}
+                 if _debugging_details;
+
+               $op->{TFD}    = $r;
+              $op->{FD}     = undef; # we don't manage this fd
+               $op->_init_filters;
+            }
+            elsif ( $op->{TYPE} eq '<pty<' ) {
+               _debug(
+                  'kid to read ', $op->{KFD}, " from pty '", $op->{PTY_ID}, "'",
+               ) if _debugging_details;
+               
+               for my $source ( $op->{SOURCE} ) {
+                  if ( UNIVERSAL::isa( $source, 'SCALAR' ) ) {
+                     _debug(
+                        "kid ", $kid->{NUM}, " to read ", $op->{KFD},
+                        " from SCALAR via pty '", $op->{PTY_ID}, "'"
+                     ) if _debugging_details;
+
+                     my $s = '';
+                     $op->{KIN_REF} = \$s;
+                  }
+                  elsif ( UNIVERSAL::isa( $source, 'CODE' ) ) {
+                     _debug(
+                        "kid ", $kid->{NUM}, " to read ", $op->{KFD},
+                        " from CODE via pty '", $op->{PTY_ID}, "'"
+                     ) if _debugging_details;
+                     my $s = '';
+                     $op->{KIN_REF} = \$s;
+                  }
+                  else {
+                     croak(
+                        "'"
+                        . ref( $source )
+                        . "' not allowed as a source for '<pty<' redirection"
+                     );
+                  }
+               }
+               $op->{FD} = $self->{PTYS}->{$op->{PTY_ID}}->fileno;
+               $op->{TFD} = undef; # The fd isn't known until after fork().
+               $op->_init_filters;
+            }
+            elsif ( $op->{TYPE} eq '>' ) {
+               ## N> output redirection.
+               my $dest = $op->{DEST};
+               if ( ! ref $dest ) {
+                  _debug(
+                     "kid ", $kid->{NUM}, " to write ", $op->{KFD},
+                     " to '", $dest, "' (write only, create, ",
+                     ( $op->{TRUNC} ? 'truncate' : 'append' ),
+                     ")"
+                  ) if _debugging_details;
+                  croak "simulated open failure"
+                     if $self->{_simulate_open_failure};
+                  $op->{TFD} = _sysopen(
+                     $dest,
+                     ( O_WRONLY
+                     | O_CREAT 
+                     | ( $op->{TRUNC} ? O_TRUNC : O_APPEND )
+                     )
+                  );
+                 if ( Win32_MODE ) {
+                    ## I have no idea why this is needed to make the current
+                    ## file position survive the gyrations TFD must go 
+                    ## through...
+                    POSIX::lseek( $op->{TFD}, 0, POSIX::SEEK_END() );
+                 }
+                  push @close_on_fail, $op->{TFD};
+               }
+               elsif ( UNIVERSAL::isa( $dest, 'GLOB' ) ) {
+                  croak(
+                   "Unopened filehandle in output redirect, command $kid->{NUM}"
+                  ) unless defined fileno $dest;
+                  ## Turn on autoflush, mostly just to flush out
+                  ## existing output.
+                  my $old_fh = select( $dest ); $| = 1; select( $old_fh );
+                  $op->{TFD} = fileno $dest;
+                  _debug(
+                     'kid to write ', $op->{KFD}, ' to handle ', $op->{TFD}
+                  ) if _debugging_details;
+               }
+               elsif ( UNIVERSAL::isa( $dest, 'SCALAR' ) ) {
+                  _debug(
+                     "kid ", $kid->{NUM}, " to write $op->{KFD} to SCALAR"
+                  ) if _debugging_details;
+
+                 $op->open_pipe( $self->_debug_fd );
+                  push @close_on_fail, $op->{FD}, $op->{TFD};
+                  $$dest = '' if $op->{TRUNC};
+               }
+               elsif ( UNIVERSAL::isa( $dest, 'CODE' ) ) {
+                  _debug(
+                     "kid $kid->{NUM} to write $op->{KFD} to CODE"
+                  ) if _debugging_details;
+
+                 $op->open_pipe( $self->_debug_fd );
+                  push @close_on_fail, $op->{FD}, $op->{TFD};
+               }
+               else {
+                  croak(
+                     "'"
+                     . ref( $dest )
+                     . "' not allowed as a sink for output redirection"
+                  );
+               }
+               $output_fds_accum[$op->{KFD}] = $op;
+               $op->_init_filters;
+            }
+
+            elsif ( $op->{TYPE} eq '>pipe' ) {
+               ## N> output redirection to a pipe we open, but don't select()
+               ## on.
+               _debug(
+                  "kid ", $kid->{NUM}, " to write ", $op->{KFD},
+                 ' to a pipe IPC::Run opens and returns'
+               ) if _debugging_details;
+
+               my ( $r, $w ) = $op->open_pipe( $self->_debug_fd, $op->{DEST} );
+              _debug "caller will read from ", fileno $op->{DEST}
+                 if _debugging_details;
+
+               $op->{TFD} = $w;
+              $op->{FD}  = undef; # we don't manage this fd
+               $op->_init_filters;
+
+               $output_fds_accum[$op->{KFD}] = $op;
+            }
+            elsif ( $op->{TYPE} eq '>pty>' ) {
+               my $dest = $op->{DEST};
+               if ( UNIVERSAL::isa( $dest, 'SCALAR' ) ) {
+                  _debug(
+                     "kid ", $kid->{NUM}, " to write ", $op->{KFD},
+                     " to SCALAR via pty '", $op->{PTY_ID}, "'"
+               ) if _debugging_details;
+
+                  $$dest = '' if $op->{TRUNC};
+               }
+               elsif ( UNIVERSAL::isa( $dest, 'CODE' ) ) {
+                  _debug(
+                     "kid ", $kid->{NUM}, " to write ", $op->{KFD},
+                     " to CODE via pty '", $op->{PTY_ID}, "'"
+                  ) if _debugging_details;
+               }
+               else {
+                  croak(
+                     "'"
+                     . ref( $dest )
+                     . "' not allowed as a sink for output redirection"
+                  );
+               }
+
+               $op->{FD} = $self->{PTYS}->{$op->{PTY_ID}}->fileno;
+               $op->{TFD} = undef; # The fd isn't known until after fork().
+               $output_fds_accum[$op->{KFD}] = $op;
+               $op->_init_filters;
+            }
+            elsif ( $op->{TYPE} eq '|' ) {
+               _debug(
+                  "pipelining $kid->{NUM} and "
+                  . ( $kid->{NUM} + 1 )
+               ) if _debugging_details;
+               ( $pipe_read_fd, $op->{TFD} ) = _pipe;
+              if ( Win32_MODE ) {
+                 _dont_inherit( $pipe_read_fd );
+                 _dont_inherit( $op->{TFD} );
+              }
+               @output_fds_accum = ();
+            }
+            elsif ( $op->{TYPE} eq '&' ) {
+               @output_fds_accum = ();
+            } # end if $op->{TYPE} tree
+           1;
+        }; # end eval
+        unless ( $ok ) {
+           push @errs, $@;
+           _debug 'caught ', $@ if _debugging;
+        }
+      } # end for ( OPS }
+   }
+
+   if ( @errs ) {
+      for ( @close_on_fail ) {
+         _close( $_ );
+         $_ = undef;
+      }
+      for ( keys %{$self->{PTYS}} ) {
+         next unless $self->{PTYS}->{$_};
+         close $self->{PTYS}->{$_};
+         $self->{PTYS}->{$_} = undef;
+      }
+      die join( '', @errs )
+   }
+
+   ## give all but the last child all of the output file descriptors
+   ## These will be reopened (and thus rendered useless) if the child
+   ## dup2s on to these descriptors, since we unshift these.  This way
+   ## each process emits output to the same file descriptors that the
+   ## last child will write to.  This is probably not quite correct,
+   ## since each child should write to the file descriptors inherited
+   ## from the parent.
+   ## TODO: fix the inheritance of output file descriptors.
+   ## NOTE: This sharing of OPS among kids means that we can't easily put
+   ## a kid number in each OPS structure to ping the kid when all ops
+   ## have closed (when $self->{PIPES} has emptied).  This means that we
+   ## need to scan the KIDS whenever @{$self->{PIPES}} is empty to see
+   ## if there any of them are still alive.
+   for ( my $num = 0; $num < $#{$self->{KIDS}}; ++$num ) {
+      for ( reverse @output_fds_accum ) {
+         next unless defined $_;
+         _debug(
+            'kid ', $self->{KIDS}->[$num]->{NUM}, ' also to write ', $_->{KFD},
+            ' to ', ref $_->{DEST}
+         ) if _debugging_details;
+         unshift @{$self->{KIDS}->[$num]->{OPS}}, $_;
+      }
+   }
+
+   ## Open the debug pipe if we need it
+   ## Create the list of PIPES we need to scan and the bit vectors needed by
+   ## select().  Do this first so that _cleanup can _clobber() them if an
+   ## exception occurs.
+   @{$self->{PIPES}} = ();
+   $self->{RIN} = '';
+   $self->{WIN} = '';
+   $self->{EIN} = '';
+   ## PIN is a vec()tor that indicates who's paused.
+   $self->{PIN} = '';
+   for my $kid ( @{$self->{KIDS}} ) {
+      for ( @{$kid->{OPS}} ) {
+         if ( defined $_->{FD} ) {
+            _debug(
+               'kid ', $kid->{NUM}, '[', $kid->{PID}, "]'s ", $_->{KFD},
+               ' is my ', $_->{FD}
+            ) if _debugging_details;
+            vec( $self->{ $_->{TYPE} =~ /^</ ? 'WIN' : 'RIN' }, $_->{FD}, 1 ) = 1;
+#          vec( $self->{EIN}, $_->{FD}, 1 ) = 1;
+            push @{$self->{PIPES}}, $_;
+         }
+      }
+   }
+
+   for my $io ( @{$self->{IOS}} ) {
+      my $fd = $io->fileno;
+      vec( $self->{RIN}, $fd, 1 ) = 1 if $io->mode =~ /r/;
+      vec( $self->{WIN}, $fd, 1 ) = 1 if $io->mode =~ /w/;
+#      vec( $self->{EIN}, $fd, 1 ) = 1;
+      push @{$self->{PIPES}}, $io;
+   }
+
+   ## Put filters on the end of the filter chains to read & write the pipes.
+   ## Clear pipe states
+   for my $pipe ( @{$self->{PIPES}} ) {
+      $pipe->{SOURCE_EMPTY} = 0;
+      $pipe->{PAUSED} = 0;
+      if ( $pipe->{TYPE} =~ /^>/ ) {
+         my $pipe_reader = sub {
+            my ( undef, $out_ref ) = @_;
+
+            return undef unless defined $pipe->{FD};
+            return 0 unless vec( $self->{ROUT}, $pipe->{FD}, 1 );
+
+            vec( $self->{ROUT}, $pipe->{FD}, 1 ) = 0;
+
+            _debug_desc_fd( 'reading from', $pipe ) if _debugging_details;
+            my $in = eval { _read( $pipe->{FD} ) };
+            if ( $@ ) {
+               $in = '';
+               ## IO::Pty throws the Input/output error if the kid dies.
+              ## read() throws the bad file descriptor message if the
+              ## kid dies on Win32.
+               die $@ unless
+                 $@ =~ $_EIO ||
+                 ($@ =~ /input or output/ && $^O =~ /aix/) 
+                 || ( Win32_MODE && $@ =~ /Bad file descriptor/ );
+            }
+
+            unless ( length $in ) {
+               $self->_clobber( $pipe );
+               return undef;
+            }
+
+            ## Protect the position so /.../g matches may be used.
+            my $pos = pos $$out_ref;
+            $$out_ref .= $in;
+            pos( $$out_ref ) = $pos;
+            return 1;
+         };
+         ## Input filters are the last filters
+         push @{$pipe->{FILTERS}}, $pipe_reader;
+         push @{$self->{TEMP_FILTERS}}, $pipe_reader;
+      }
+      else {
+         my $pipe_writer = sub {
+            my ( $in_ref, $out_ref ) = @_;
+            return undef unless defined $pipe->{FD};
+            return 0
+               unless vec( $self->{WOUT}, $pipe->{FD}, 1 )
+                  || $pipe->{PAUSED};
+
+            vec( $self->{WOUT}, $pipe->{FD}, 1 ) = 0;
+
+            if ( ! length $$in_ref ) {
+               if ( ! defined get_more_input ) {
+                  $self->_clobber( $pipe );
+                  return undef;
+               }
+            }
+
+            unless ( length $$in_ref ) {
+               unless ( $pipe->{PAUSED} ) {
+                  _debug_desc_fd( 'pausing', $pipe ) if _debugging_details;
+                  vec( $self->{WIN}, $pipe->{FD}, 1 ) = 0;
+#                vec( $self->{EIN}, $pipe->{FD}, 1 ) = 0;
+                  vec( $self->{PIN}, $pipe->{FD}, 1 ) = 1;
+                  $pipe->{PAUSED} = 1;
+               }
+               return 0;
+            }
+            _debug_desc_fd( 'writing to', $pipe ) if _debugging_details;
+
+            my $c = _write( $pipe->{FD}, $$in_ref );
+            substr( $$in_ref, 0, $c, '' );
+            return 1;
+         };
+         ## Output filters are the first filters
+         unshift @{$pipe->{FILTERS}}, $pipe_writer;
+         push    @{$self->{TEMP_FILTERS}}, $pipe_writer;
+      }
+   }
+}
+
+
+sub _dup2_gently {
+   ## A METHOD, NOT A FUNCTION, NEEDS $self!
+   my IPC::Run $self = shift;
+   my ( $files, $fd1, $fd2 ) = @_;
+   ## Moves TFDs that are using the destination fd out of the
+   ## way before calling _dup2
+   for ( @$files ) {
+      next unless defined $_->{TFD};
+      $_->{TFD} = _dup( $_->{TFD} ) if $_->{TFD} == $fd2;
+   }
+   $self->{DEBUG_FD} = _dup $self->{DEBUG_FD}
+      if defined $self->{DEBUG_FD} && $self->{DEBUG_FD} == $fd2;
+
+   _dup2_rudely( $fd1, $fd2 );
+}
+
+=pod
+
+=item close_terminal
+
+This is used as (or in) an init sub to cast off the bonds of a controlling
+terminal.  It must precede all other redirection ops that affect
+STDIN, STDOUT, or STDERR to be guaranteed effective.
+
+=cut
+
+
+sub close_terminal {
+   ## Cast of the bonds of a controlling terminal
+
+   POSIX::setsid() || croak "POSIX::setsid() failed";
+   _debug "closing stdin, out, err"
+      if _debugging_details;
+   close STDIN;
+   close STDERR;
+   close STDOUT;
+}
+
+
+sub _do_kid_and_exit {
+   my IPC::Run $self = shift;
+   my ( $kid ) = @_;
+
+   my ( $s1, $s2 );
+   if ($] < 5.008) {
+     ## For unknown reasons, placing these two statements in the eval{}
+     ## causes the eval {} to not catch errors after they are executed in
+     ## perl 5.6.0, godforsaken version that it is...not sure about 5.6.1.
+     ## Part of this could be that these symbols get destructed when
+     ## exiting the eval, and that destruction might be what's (wrongly)
+     ## confusing the eval{}, allowing the exception to probpogate.
+     $s1 = Symbol::gensym();
+     $s2 = Symbol::gensym();
+   }
+
+   eval {
+      local $cur_self = $self;
+
+      if ( _debugging ) {
+         _set_child_debug_name( ref $kid->{VAL} eq "CODE"
+                ? "CODE"
+                : basename( $kid->{VAL}->[0] )
+         );
+      }
+
+      ## close parent FD's first so they're out of the way.
+      ## Don't close STDIN, STDOUT, STDERR: they should be inherited or
+      ## overwritten below.
+      my @needed = $self->{noinherit} ? () : ( 1, 1, 1 );
+      $needed[ $self->{SYNC_WRITER_FD} ] = 1;
+      $needed[ $self->{DEBUG_FD} ] = 1 if defined $self->{DEBUG_FD};
+
+      for ( @{$kid->{OPS}} ) {
+        $needed[ $_->{TFD} ] = 1 if defined $_->{TFD};
+      }
+
+      ## TODO: use the forthcoming IO::Pty to close the terminal and
+      ## make the first pty for this child the controlling terminal.
+      ## This will also make it so that pty-laden kids don't cause
+      ## other kids to lose stdin/stdout/stderr.
+      my @closed;
+      if ( %{$self->{PTYS}} ) {
+        ## Clean up the parent's fds.
+        for ( keys %{$self->{PTYS}} ) {
+           _debug "Cleaning up parent's ptty '$_'" if _debugging_details;
+           my $slave = $self->{PTYS}->{$_}->slave;
+           $closed[ $self->{PTYS}->{$_}->fileno ] = 1;
+           close $self->{PTYS}->{$_};
+           $self->{PTYS}->{$_} = $slave;
+        }
+
+        close_terminal;
+        $closed[ $_ ] = 1 for ( 0..2 );
+      }
+
+      for my $sibling ( @{$self->{KIDS}} ) {
+        for ( @{$sibling->{OPS}} ) {
+           if ( $_->{TYPE} =~ /^.pty.$/ ) {
+              $_->{TFD} = $self->{PTYS}->{$_->{PTY_ID}}->fileno;
+              $needed[$_->{TFD}] = 1;
+           }
+
+#          for ( $_->{FD}, ( $sibling != $kid ? $_->{TFD} : () ) ) {
+#             if ( defined $_ && ! $closed[$_] && ! $needed[$_] ) {
+#                _close( $_ );
+#                $closed[$_] = 1;
+#                $_ = undef;
+#             }
+#          }
+        }
+      }
+
+      ## This is crude: we have no way of keeping track of browsing all open
+      ## fds, so we scan to a fairly high fd.
+      _debug "open fds: ", join " ", keys %fds if _debugging_details;
+      for (keys %fds) {
+         if ( ! $closed[$_] && ! $needed[$_] ) {
+            _close( $_ );
+            $closed[$_] = 1;
+         }
+      }
+
+      ## Lazy closing is so the same fd (ie the same TFD value) can be dup2'ed on
+      ## several times.
+      my @lazy_close;
+      for ( @{$kid->{OPS}} ) {
+        if ( defined $_->{TFD} ) {
+           unless ( $_->{TFD} == $_->{KFD} ) {
+              $self->_dup2_gently( $kid->{OPS}, $_->{TFD}, $_->{KFD} );
+              push @lazy_close, $_->{TFD};
+           }
+        }
+        elsif ( $_->{TYPE} eq 'dup' ) {
+           $self->_dup2_gently( $kid->{OPS}, $_->{KFD1}, $_->{KFD2} )
+              unless $_->{KFD1} == $_->{KFD2};
+        }
+        elsif ( $_->{TYPE} eq 'close' ) {
+           for ( $_->{KFD} ) {
+              if ( ! $closed[$_] ) {
+                 _close( $_ );
+                 $closed[$_] = 1;
+                 $_ = undef;
+              }
+           }
+        }
+        elsif ( $_->{TYPE} eq 'init' ) {
+           $_->{SUB}->();
+        }
+      }
+
+      for ( @lazy_close ) {
+        unless ( $closed[$_] ) {
+           _close( $_ );
+           $closed[$_] = 1;
+        }
+      }
+
+      if ( ref $kid->{VAL} ne 'CODE' ) {
+        open $s1, ">&=$self->{SYNC_WRITER_FD}"
+           or croak "$! setting filehandle to fd SYNC_WRITER_FD";
+        fcntl $s1, F_SETFD, 1;
+
+        if ( defined $self->{DEBUG_FD} ) {
+           open $s2, ">&=$self->{DEBUG_FD}"
+              or croak "$! setting filehandle to fd DEBUG_FD";
+           fcntl $s2, F_SETFD, 1;
+        }
+
+        if ( _debugging ) {
+           my @cmd = ( $kid->{PATH}, @{$kid->{VAL}}[1..$#{$kid->{VAL}}] );
+           _debug 'execing ', join " ", map { /[\s\"]/ ? "'$_'" : $_ } @cmd;
+        }
+
+        die "exec failed: simulating exec() failure"
+           if $self->{_simulate_exec_failure};
+
+        _exec $kid->{PATH}, @{$kid->{VAL}}[1..$#{$kid->{VAL}}];
+
+        croak "exec failed: $!";
+      }
+   };
+   if ( $@ ) {
+      _write $self->{SYNC_WRITER_FD}, $@;
+      ## Avoid DESTROY.
+      POSIX::exit 1;
+   }
+
+   ## We must be executing code in the child, otherwise exec() would have
+   ## prevented us from being here.
+   _close $self->{SYNC_WRITER_FD};
+   _debug 'calling fork()ed CODE ref' if _debugging;
+   POSIX::close $self->{DEBUG_FD}      if defined $self->{DEBUG_FD};
+   ## TODO: Overload CORE::GLOBAL::exit...
+   $kid->{VAL}->();
+
+   ## There are bugs in perl closures up to and including 5.6.1
+   ## that may keep this next line from having any effect, and it
+   ## won't have any effect if our caller has kept a copy of it, but
+   ## this may cause the closure to be cleaned up.  Maybe.
+   $kid->{VAL} = undef;
+
+   ## Use POSIX::exit to avoid global destruction, since this might
+   ## cause DESTROY() to be called on objects created in the parent
+   ## and thus cause double cleanup.  For instance, if DESTROY() unlinks
+   ## a file in the child, we don't want the parent to suddenly miss
+   ## it.
+   POSIX::exit 0;
+}
+
+=pod
+
+=item start
+
+   $h = start(
+      \@cmd, \$in, \$out, ...,
+      timeout( 30, name => "process timeout" ),
+      $stall_timeout = timeout( 10, name => "stall timeout"   ),
+   );
+
+   $h = start \@cmd, '<', \$in, '|', \@cmd2, ...;
+
+start() accepts a harness or harness specification and returns a harness
+after building all of the pipes and launching (via fork()/exec(), or, maybe
+someday, spawn()) all the child processes.  It does not send or receive any
+data on the pipes, see pump() and finish() for that.
+
+You may call harness() and then pass it's result to start() if you like,
+but you only need to if it helps you structure or tune your application.
+If you do call harness(), you may skip start() and proceed directly to
+pump.
+
+start() also starts all timers in the harness.  See L<IPC::Run::Timer>
+for more information.
+
+start() flushes STDOUT and STDERR to help you avoid duplicate output.
+It has no way of asking Perl to flush all your open filehandles, so
+you are going to need to flush any others you have open.  Sorry.
+
+Here's how if you don't want to alter the state of $| for your
+filehandle:
+
+   $ofh = select HANDLE; $of = $|; $| = 1; $| = $of; select $ofh;
+
+If you don't mind leaving output unbuffered on HANDLE, you can do
+the slightly shorter
+
+   $ofh = select HANDLE; $| = 1; select $ofh;
+
+Or, you can use IO::Handle's flush() method:
+
+   use IO::Handle;
+   flush HANDLE;
+
+Perl needs the equivalent of C's fflush( (FILE *)NULL ).
+
+=cut
+
+sub start {
+# $SIG{__DIE__} = sub { my $s = shift; Carp::cluck $s; die $s };
+   my $options;
+   if ( @_ && ref $_[-1] eq 'HASH' ) {
+      $options = pop;
+      require Data::Dumper;
+      carp "Passing in options as a hash is deprecated:\n", Data::Dumper::Dumper( $options );
+   }
+
+   my IPC::Run $self;
+   if ( @_ == 1 && UNIVERSAL::isa( $_[0], __PACKAGE__ ) ) {
+      $self = shift;
+      $self->{$_} = $options->{$_} for keys %$options;
+   }
+   else {
+      $self = harness( @_, $options ? $options : () );
+   }
+
+   local $cur_self = $self;
+
+   $self->kill_kill if $self->{STATE} == _started;
+
+   _debug "** starting" if _debugging;
+
+   $_->{RESULT} = undef for @{$self->{KIDS}};
+
+   ## Assume we're not being called from &run.  It will correct our
+   ## assumption if need be.  This affects whether &_select_loop clears
+   ## input queues to '' when they're empty.
+   $self->{clear_ins} = 1;
+
+   IPC::Run::Win32Helper::optimize $self
+       if Win32_MODE && $in_run;
+
+   my @errs;
+
+   for ( @{$self->{TIMERS}} ) {
+      eval { $_->start };
+      if ( $@ ) {
+         push @errs, $@;
+         _debug 'caught ', $@ if _debugging;
+      }
+   }
+
+   eval { $self->_open_pipes };
+   if ( $@ ) {
+      push @errs, $@;
+      _debug 'caught ', $@ if _debugging;
+   }
+
+   if ( ! @errs ) {
+      ## This is a bit of a hack, we should do it for all open filehandles.
+      ## Since there's no way I know of to enumerate open filehandles, we
+      ## autoflush STDOUT and STDERR.  This is done so that the children don't
+      ## inherit output buffers chock full o' redundant data.  It's really
+      ## confusing to track that down.
+      { my $ofh = select STDOUT; local $| = 1; select $ofh; }
+      { my $ofh = select STDERR; local $| = 1; select $ofh; }
+      for my $kid ( @{$self->{KIDS}} ) {
+         $kid->{RESULT} = undef;
+         _debug "child: ",
+            ref( $kid->{VAL} ) eq "CODE"
+            ? "CODE ref"
+            : (
+               "`",
+               join( " ", map /[^\w.-]/ ? "'$_'" : $_, @{$kid->{VAL}} ),
+               "`"
+            ) if _debugging_details;
+         eval {
+            croak "simulated failure of fork"
+               if $self->{_simulate_fork_failure};
+            unless ( Win32_MODE ) {
+              $self->_spawn( $kid );
+            }
+            else {
+## TODO: Test and debug spawning code.  Someday.
+               _debug( 
+                  'spawning ',
+                  join(
+                     ' ',
+                     map(
+                        "'$_'",
+                        ( $kid->{PATH}, @{$kid->{VAL}}[1..$#{$kid->{VAL}}] )
+                     )
+                  )
+               ) if _debugging;
+              ## The external kid wouldn't know what to do with it anyway.
+              ## This is only used by the "helper" pump processes on Win32.
+              _dont_inherit( $self->{DEBUG_FD} );
+               ( $kid->{PID}, $kid->{PROCESS} ) =
+                 IPC::Run::Win32Helper::win32_spawn( 
+                    [ $kid->{PATH}, @{$kid->{VAL}}[1..$#{$kid->{VAL}}] ],
+                    $kid->{OPS},
+                 );
+               _debug "spawn() = ", $kid->{PID} if _debugging;
+            }
+         };
+         if ( $@ ) {
+            push @errs, $@;
+            _debug 'caught ', $@ if _debugging;
+         }
+      }
+   }
+
+   ## Close all those temporary filehandles that the kids needed.
+   for my $pty ( values %{$self->{PTYS}} ) {
+      close $pty->slave;
+   }
+
+   my @closed;
+   for my $kid ( @{$self->{KIDS}} ) {
+      for ( @{$kid->{OPS}} ) {
+         my $close_it = eval {
+            defined $_->{TFD}
+               && ! $_->{DONT_CLOSE}
+               && ! $closed[$_->{TFD}]
+               && ( ! Win32_MODE || ! $_->{RECV_THROUGH_TEMP_FILE} ) ## Win32 hack
+         };
+         if ( $@ ) {
+            push @errs, $@;
+            _debug 'caught ', $@ if _debugging;
+         }
+         if ( $close_it || $@ ) {
+            eval {
+               _close( $_->{TFD} );
+               $closed[$_->{TFD}] = 1;
+               $_->{TFD} = undef;
+            };
+            if ( $@ ) {
+               push @errs, $@;
+               _debug 'caught ', $@ if _debugging;
+            }
+         }
+      }
+   }
+confess "gak!" unless defined $self->{PIPES};
+
+   if ( @errs ) {
+      eval { $self->_cleanup };
+      warn $@ if $@;
+      die join( '', @errs );
+   }
+
+   $self->{STATE} = _started;
+   return $self;
+}
+
+=item adopt
+
+Experimental feature. NOT FUNCTIONAL YET, NEED TO CLOSE FDS BETTER IN CHILDREN.  SEE t/adopt.t for a test suite.
+
+=cut
+
+sub adopt {
+   my IPC::Run $self = shift;
+
+   for my $adoptee ( @_ ) {
+      push @{$self->{IOS}},    @{$adoptee->{IOS}};
+      ## NEED TO RENUMBER THE KIDS!!
+      push @{$self->{KIDS}},   @{$adoptee->{KIDS}};
+      push @{$self->{PIPES}},  @{$adoptee->{PIPES}};
+      $self->{PTYS}->{$_} = $adoptee->{PTYS}->{$_}
+         for keys %{$adoptee->{PYTS}};
+      push @{$self->{TIMERS}}, @{$adoptee->{TIMERS}};
+      $adoptee->{STATE} = _finished;
+   }
+}
+
+
+sub _clobber {
+   my IPC::Run $self = shift;
+   my ( $file ) = @_;
+   _debug_desc_fd( "closing", $file ) if _debugging_details;
+   my $doomed = $file->{FD};
+   my $dir = $file->{TYPE} =~ /^</ ? 'WIN' : 'RIN';
+   vec( $self->{$dir}, $doomed, 1 ) = 0;
+#   vec( $self->{EIN},  $doomed, 1 ) = 0;
+   vec( $self->{PIN},  $doomed, 1 ) = 0;
+   if ( $file->{TYPE} =~ /^(.)pty.$/ ) {
+      if ( $1 eq '>' ) {
+         ## Only close output ptys.  This is so that ptys as inputs are
+         ## never autoclosed, which would risk losing data that was
+         ## in the slave->parent queue.
+         _debug_desc_fd "closing pty", $file if _debugging_details;
+         close $self->{PTYS}->{$file->{PTY_ID}}
+            if defined $self->{PTYS}->{$file->{PTY_ID}};
+         $self->{PTYS}->{$file->{PTY_ID}} = undef;
+      }
+   }
+   elsif ( UNIVERSAL::isa( $file, 'IPC::Run::IO' ) ) {
+      $file->close unless $file->{DONT_CLOSE};
+   }
+   else {
+      _close( $doomed );
+   }
+
+   @{$self->{PIPES}} = grep
+      defined $_->{FD} && ( $_->{TYPE} ne $file->{TYPE} || $_->{FD} ne $doomed),
+      @{$self->{PIPES}};
+
+   $file->{FD} = undef;
+}
+
+sub _select_loop {
+   my IPC::Run $self = shift;
+
+   my $io_occurred;
+
+   my $not_forever = 0.01;
+
+SELECT:
+   while ( $self->pumpable ) {
+      if ( $io_occurred && $self->{break_on_io} ) {
+         _debug "exiting _select(): io occured and break_on_io set"
+           if _debugging_details;
+         last;
+      }
+
+      my $timeout = $self->{non_blocking} ? 0 : undef;
+
+      if ( @{$self->{TIMERS}} ) {
+         my $now = time;
+         my $time_left;
+         for ( @{$self->{TIMERS}} ) {
+            next unless $_->is_running;
+            $time_left = $_->check( $now );
+            ## Return when a timer expires
+            return if defined $time_left && ! $time_left;
+            $timeout = $time_left
+               if ! defined $timeout || $time_left < $timeout;
+         }
+      }
+
+      ##
+      ## See if we can unpause any input channels
+      ##
+      my $paused = 0;
+
+      for my $file ( @{$self->{PIPES}} ) {
+         next unless $file->{PAUSED} && $file->{TYPE} =~ /^</;
+
+         _debug_desc_fd( "checking for more input", $file ) if _debugging_details;
+         my $did;
+         1 while $did = $file->_do_filters( $self );
+         if ( defined $file->{FD} && ! defined( $did ) || $did ) {
+            _debug_desc_fd( "unpausing", $file ) if _debugging_details;
+            $file->{PAUSED} = 0;
+            vec( $self->{WIN}, $file->{FD}, 1 ) = 1;
+#          vec( $self->{EIN}, $file->{FD}, 1 ) = 1;
+            vec( $self->{PIN}, $file->{FD}, 1 ) = 0;
+         }
+         else {
+            ## This gets incremented occasionally when the IO channel
+            ## was actually closed.  That's a bug, but it seems mostly
+            ## harmless: it causes us to exit if break_on_io, or to set
+            ## the timeout to not be forever.  I need to fix it, though.
+            ++$paused;
+         }
+      }
+
+      if ( _debugging_details ) {
+         my $map = join(
+            '',
+            map {
+               my $out;
+               $out = 'r'                     if vec( $self->{RIN}, $_, 1 );
+               $out = $out ? 'b' : 'w'        if vec( $self->{WIN}, $_, 1 );
+               $out = 'p'           if ! $out && vec( $self->{PIN}, $_, 1 );
+               $out = $out ? uc( $out ) : 'x' if vec( $self->{EIN}, $_, 1 );
+               $out = '-' unless $out;
+               $out;
+            } (0..1024)
+         );
+         $map =~ s/((?:[a-zA-Z-]|\([^\)]*\)){12,}?)-*$/$1/;
+         _debug 'fds for select: ', $map if _debugging_details;
+      }
+
+      ## _do_filters may have closed our last fd, and we need to see if
+      ## we have I/O, or are just waiting for children to exit.
+      my $p = $self->pumpable;
+      last unless $p;
+      if ( $p != 0  && ( ! defined $timeout || $timeout > 0.1 ) ) {
+         ## No I/O will wake the select loop up, but we have children
+         ## lingering, so we need to poll them with a short timeout.
+        ## Otherwise, assume more input will be coming.
+        $timeout = $not_forever;
+         $not_forever *= 2;
+         $not_forever = 0.5 if $not_forever >= 0.5;
+      }
+
+      ## Make sure we don't block forever in select() because inputs are
+      ## paused.
+      if ( ! defined $timeout && ! ( @{$self->{PIPES}} - $paused ) ) {
+         ## Need to return if we're in pump and all input is paused, or
+        ## we'll loop until all inputs are unpaused, which is darn near
+        ## forever.  And a day.
+         if ( $self->{break_on_io} ) {
+           _debug "exiting _select(): no I/O to do and timeout=forever"
+               if _debugging;
+           last;
+        }
+
+        ## Otherwise, assume more input will be coming.
+        $timeout = $not_forever;
+         $not_forever *= 2;
+         $not_forever = 0.5 if $not_forever >= 0.5;
+      }
+
+      _debug 'timeout=', defined $timeout ? $timeout : 'forever'
+         if _debugging_details;
+
+      my $nfound;
+      unless ( Win32_MODE ) {
+         $nfound = select(
+            $self->{ROUT} = $self->{RIN},
+            $self->{WOUT} = $self->{WIN},
+            $self->{EOUT} = $self->{EIN},
+            $timeout 
+        );
+      }
+      else {
+        my @in = map $self->{$_}, qw( RIN WIN EIN );
+        ## Win32's select() on Win32 seems to die if passed vectors of
+        ## all 0's.  Need to report this when I get back online.
+        for ( @in ) {
+           $_ = undef unless index( ( unpack "b*", $_ ), 1 ) >= 0;
+        }
+
+        $nfound = select(
+            $self->{ROUT} = $in[0],
+            $self->{WOUT} = $in[1],
+            $self->{EOUT} = $in[2],
+            $timeout 
+         );
+
+        for ( $self->{ROUT}, $self->{WOUT}, $self->{EOUT} ) {
+           $_ = "" unless defined $_;
+        }
+      }
+      last if ! $nfound && $self->{non_blocking};
+
+      if ($nfound < 0) {
+         if ($! == POSIX::EINTR) {
+            # Caught a signal before any FD went ready.  Ensure that
+            # the bit fields reflect "no FDs ready".
+            $self->{ROUT} = $self->{WOUT} = $self->{EOUT} = '';
+            $nfound = 0;
+         }
+         else {
+            croak "$! in select";
+         }
+      }
+          ## TODO: Analyze the EINTR failure mode and see if this patch
+          ## is adequate and optimal.
+          ## TODO: Add an EINTR test to the test suite.
+
+      if ( _debugging_details ) {
+         my $map = join(
+            '',
+            map {
+               my $out;
+               $out = 'r'                     if vec( $self->{ROUT}, $_, 1 );
+               $out = $out ? 'b' : 'w'        if vec( $self->{WOUT}, $_, 1 );
+               $out = $out ? uc( $out ) : 'x' if vec( $self->{EOUT}, $_, 1 );
+               $out = '-' unless $out;
+               $out;
+            } (0..128)
+         );
+         $map =~ s/((?:[a-zA-Z-]|\([^\)]*\)){12,}?)-*$/$1/;
+         _debug "selected  ", $map;
+      }
+
+      ## Need to copy since _clobber alters @{$self->{PIPES}}.
+      ## TODO: Rethink _clobber().  Rethink $file->{PAUSED}, too.
+      my @pipes = @{$self->{PIPES}};
+      $io_occurred = $_->poll( $self ) ? 1 : $io_occurred for @pipes;
+#   FILE:
+#      for my $pipe ( @pipes ) {
+#         ## Pipes can be shared among kids.  If another kid closes the
+#         ## pipe, then it's {FD} will be undef.  Also, on Win32, pipes can
+#       ## be optimized to be files, in which case the FD is left undef
+#       ## so we don't try to select() on it.
+#         if ( $pipe->{TYPE} =~ /^>/
+#            && defined $pipe->{FD}
+#            && vec( $self->{ROUT}, $pipe->{FD}, 1 )
+#         ) {
+#            _debug_desc_fd( "filtering data from", $pipe ) if _debugging_details;
+#confess "phooey" unless UNIVERSAL::isa( $pipe, "IPC::Run::IO" );
+#            $io_occurred = 1 if $pipe->_do_filters( $self );
+#
+#            next FILE unless defined $pipe->{FD};
+#         }
+#
+#       ## On Win32, pipes to the child can be optimized to be files
+#       ## and FD left undefined so we won't select on it.
+#         if ( $pipe->{TYPE} =~ /^</
+#            && defined $pipe->{FD}
+#            && vec( $self->{WOUT}, $pipe->{FD}, 1 )
+#         ) {
+#            _debug_desc_fd( "filtering data to", $pipe ) if _debugging_details;
+#            $io_occurred = 1 if $pipe->_do_filters( $self );
+#
+#            next FILE unless defined $pipe->{FD};
+#         }
+#
+#         if ( defined $pipe->{FD} && vec( $self->{EOUT}, $pipe->{FD}, 1 ) ) {
+#            ## BSD seems to sometimes raise the exceptional condition flag
+#            ## when a pipe is closed before we read it's last data.  This
+#            ## causes spurious warnings and generally renders the exception
+#            ## mechanism useless for our purposes.  The exception
+#            ## flag semantics are too variable (they're device driver
+#            ## specific) for me to easily map to any automatic action like
+#            ## warning or croaking (try running v0.42 if you don't believe me
+#            ## :-).
+#            warn "Exception on descriptor $pipe->{FD}";
+#         }
+#      }
+   }
+
+   return;
+}
+
+
+sub _cleanup {
+   my IPC::Run $self = shift;
+   _debug "cleaning up" if _debugging_details;
+
+   for ( values %{$self->{PTYS}} ) {
+      next unless ref $_;
+      eval {
+         _debug "closing slave fd ", fileno $_->slave if _debugging_data;
+         close $_->slave;
+      };
+      carp $@ . " while closing ptys" if $@;
+      eval {
+         _debug "closing master fd ", fileno $_ if _debugging_data;
+         close $_;
+      };
+      carp $@ . " closing ptys" if $@;
+   }
+   
+   _debug "cleaning up pipes" if _debugging_details;
+   ## _clobber modifies PIPES
+   $self->_clobber( $self->{PIPES}->[0] ) while @{$self->{PIPES}};
+
+   for my $kid ( @{$self->{KIDS}} ) {
+      _debug "cleaning up kid ", $kid->{NUM} if _debugging_details;
+      if ( ! length $kid->{PID} ) {
+         _debug 'never ran child ', $kid->{NUM}, ", can't reap"
+            if _debugging;
+         for my $op ( @{$kid->{OPS}} ) {
+            _close( $op->{TFD} )
+               if defined $op->{TFD} && ! defined $op->{TEMP_FILE_HANDLE};
+         }
+      }
+      elsif ( ! defined $kid->{RESULT} ) {
+         _debug 'reaping child ', $kid->{NUM}, ' (pid ', $kid->{PID}, ')'
+            if _debugging;
+         my $pid = waitpid $kid->{PID}, 0;
+         $kid->{RESULT} = $?;
+         _debug 'reaped ', $pid, ', $?=', $kid->{RESULT}
+            if _debugging;
+      }
+
+#      if ( defined $kid->{DEBUG_FD} ) {
+#       die;
+#         @{$kid->{OPS}} = grep
+#            ! defined $_->{KFD} || $_->{KFD} != $kid->{DEBUG_FD},
+#            @{$kid->{OPS}};
+#         $kid->{DEBUG_FD} = undef;
+#      }
+
+      _debug "cleaning up filters" if _debugging_details;
+      for my $op ( @{$kid->{OPS}} ) {
+         @{$op->{FILTERS}} = grep {
+            my $filter = $_;
+            ! grep $filter == $_, @{$self->{TEMP_FILTERS}};
+         } @{$op->{FILTERS}};
+      }
+
+      for my $op ( @{$kid->{OPS}} ) {
+         $op->_cleanup( $self ) if UNIVERSAL::isa( $op, "IPC::Run::IO" );
+      }
+   }
+   $self->{STATE} = _finished;
+   @{$self->{TEMP_FILTERS}} = ();
+   _debug "done cleaning up" if _debugging_details;
+
+   POSIX::close $self->{DEBUG_FD} if defined $self->{DEBUG_FD};
+   $self->{DEBUG_FD} = undef;
+}
+
+=pod
+
+=item pump
+
+   pump $h;
+   $h->pump;
+
+Pump accepts a single parameter harness.  It blocks until it delivers some
+input or receives some output.  It returns TRUE if there is still input or
+output to be done, FALSE otherwise.
+
+pump() will automatically call start() if need be, so you may call harness()
+then proceed to pump() if that helps you structure your application.
+
+If pump() is called after all harnessed activities have completed, a "process
+ended prematurely" exception to be thrown.  This allows for simple scripting
+of external applications without having to add lots of error handling code at
+each step of the script:
+
+   $h = harness \@smbclient, \$in, \$out, $err;
+
+   $in = "cd /foo\n";
+   $h->pump until $out =~ /^smb.*> \Z/m;
+   die "error cding to /foo:\n$out" if $out =~ "ERR";
+   $out = '';
+
+   $in = "mget *\n";
+   $h->pump until $out =~ /^smb.*> \Z/m;
+   die "error retrieving files:\n$out" if $out =~ "ERR";
+
+   $h->finish;
+
+   warn $err if $err;
+
+=cut
+
+sub pump {
+   die "pump() takes only a a single harness as a parameter"
+      unless @_ == 1 && UNIVERSAL::isa( $_[0], __PACKAGE__ );
+
+   my IPC::Run $self = shift;
+
+   local $cur_self = $self;
+
+   _debug "** pumping" 
+      if _debugging;
+
+#   my $r = eval {
+      $self->start if $self->{STATE} < _started;
+      croak "process ended prematurely" unless $self->pumpable;
+
+      $self->{auto_close_ins} = 0;
+      $self->{break_on_io}    = 1;
+      $self->_select_loop;
+      return $self->pumpable;
+#   };
+#   if ( $@ ) {
+#      my $x = $@;
+#      _debug $x if _debugging && $x;
+#      eval { $self->_cleanup };
+#      warn $@ if $@;
+#      die $x;
+#   }
+#   return $r;
+}
+
+=pod
+
+=item pump_nb
+
+   pump_nb $h;
+   $h->pump_nb;
+
+"pump() non-blocking", pumps if anything's ready to be pumped, returns
+immediately otherwise.  This is useful if you're doing some long-running
+task in the foreground, but don't want to starve any child processes.
+
+=cut
+
+sub pump_nb {
+   my IPC::Run $self = shift;
+
+   $self->{non_blocking} = 1;
+   my $r = eval { $self->pump };
+   $self->{non_blocking} = 0;
+   die $@ if $@;
+   return $r;
+}
+
+=pod
+
+=item pumpable
+
+Returns TRUE if calling pump() won't throw an immediate "process ended
+prematurely" exception.  This means that there are open I/O channels or
+active processes. May yield the parent processes' time slice for 0.01
+second if all pipes are to the child and all are paused.  In this case
+we can't tell if the child is dead, so we yield the processor and
+then attempt to reap the child in a nonblocking way.
+
+=cut
+
+## Undocumented feature (don't depend on it outside this module):
+## returns -1 if we have I/O channels open, or >0 if no I/O channels
+## open, but we have kids running.  This allows the select loop
+## to poll for child exit.
+sub pumpable {
+   my IPC::Run $self = shift;
+
+   ## There's a catch-22 we can get in to if there is only one pipe left
+   ## open to the child and it's paused (ie the SCALAR it's tied to
+   ## is '').  It's paused, so we're not select()ing on it, so we don't
+   ## check it to see if the child attached to it is alive and it stays
+   ## in @{$self->{PIPES}} forever.  So, if all pipes are paused, see if
+   ## we can reap the child.
+   return -1 if grep !$_->{PAUSED}, @{$self->{PIPES}};
+
+   ## See if the child is dead.
+   $self->reap_nb;
+   return 0 unless $self->_running_kids;
+
+   ## If we reap_nb and it's not dead yet, yield to it to see if it
+   ## exits.
+   ##
+   ## A better solution would be to unpause all the pipes, but I tried that
+   ## and it never errored on linux.  Sigh.  
+   select undef, undef, undef, 0.0001;
+
+   ## try again
+   $self->reap_nb;
+   return 0 unless $self->_running_kids;
+
+   return -1; ## There are pipes waiting
+}
+
+
+sub _running_kids {
+   my IPC::Run $self = shift;
+   return grep
+      defined $_->{PID} && ! defined $_->{RESULT},
+      @{$self->{KIDS}};
+}
+
+=pod
+
+=item reap_nb
+
+Attempts to reap child processes, but does not block.
+
+Does not currently take any parameters, one day it will allow specific
+children to be reaped.
+
+Only call this from a signal handler if your C<perl> is recent enough
+to have safe signal handling (5.6.1 did not, IIRC, but it was being discussed
+on perl5-porters).  Calling this (or doing any significant work) in a signal
+handler on older C<perl>s is asking for seg faults.
+
+=cut
+
+my $still_runnings;
+
+sub reap_nb {
+   my IPC::Run $self = shift;
+
+   local $cur_self = $self;
+
+   ## No more pipes, look to see if all the kids yet live, reaping those
+   ## that haven't.  I'd use $SIG{CHLD}/$SIG{CLD}, but that's broken
+   ## on older (SYSV) platforms and perhaps less portable than waitpid().
+   ## This could be slow with a lot of kids, but that's rare and, well,
+   ## a lot of kids is slow in the first place.
+   ## Oh, and this keeps us from reaping other children the process
+   ## may have spawned.
+   for my $kid ( @{$self->{KIDS}} ) {
+      if ( Win32_MODE ) {
+        next if ! defined $kid->{PROCESS} || defined $kid->{RESULT};
+        unless ( $kid->{PROCESS}->Wait( 0 ) ) {
+           _debug "kid $kid->{NUM} ($kid->{PID}) still running"
+               if _debugging_details;
+           next;
+        }
+
+         _debug "kid $kid->{NUM} ($kid->{PID}) exited"
+            if _debugging;
+
+        $kid->{PROCESS}->GetExitCode( $kid->{RESULT} )
+           or croak "$! while GetExitCode()ing for Win32 process";
+
+        unless ( defined $kid->{RESULT} ) {
+           $kid->{RESULT} = "0 but true";
+           $? = $kid->{RESULT} = 0x0F;
+        }
+        else {
+           $? = $kid->{RESULT} << 8;
+        }
+      }
+      else {
+        next if ! defined $kid->{PID} || defined $kid->{RESULT};
+        my $pid = waitpid $kid->{PID}, POSIX::WNOHANG();
+        unless ( $pid ) {
+           _debug "$kid->{NUM} ($kid->{PID}) still running"
+               if _debugging_details;
+           next;
+        }
+
+        if ( $pid < 0 ) {
+           _debug "No such process: $kid->{PID}\n" if _debugging;
+           $kid->{RESULT} = "unknown result, unknown PID";
+        }
+        else {
+            _debug "kid $kid->{NUM} ($kid->{PID}) exited"
+               if _debugging;
+
+           confess "waitpid returned the wrong PID: $pid instead of $kid->{PID}"
+              unless $pid = $kid->{PID};
+           _debug "$kid->{PID} returned $?\n" if _debugging;
+           $kid->{RESULT} = $?;
+        }
+      }
+   }
+}
+
+=pod
+
+=item finish
+
+This must be called after the last start() or pump() call for a harness,
+or your system will accumulate defunct processes and you may "leak"
+file descriptors.
+
+finish() returns TRUE if all children returned 0 (and were not signaled and did
+not coredump, ie ! $?), and FALSE otherwise (this is like run(), and the
+opposite of system()).
+
+Once a harness has been finished, it may be run() or start()ed again,
+including by pump()s auto-start.
+
+If this throws an exception rather than a normal exit, the harness may
+be left in an unstable state, it's best to kill the harness to get rid
+of all the child processes, etc.
+
+Specifically, if a timeout expires in finish(), finish() will not
+kill all the children.  Call C<<$h->kill_kill>> in this case if you care.
+This differs from the behavior of L</run>.
+
+=cut
+
+sub finish {
+   my IPC::Run $self = shift;
+   my $options = @_ && ref $_[-1] eq 'HASH' ? pop : {};
+
+   local $cur_self = $self;
+
+   _debug "** finishing" if _debugging;
+
+   $self->{non_blocking}   = 0;
+   $self->{auto_close_ins} = 1;
+   $self->{break_on_io}    = 0;
+   # We don't alter $self->{clear_ins}, start() and run() control it.
+
+   while ( $self->pumpable ) {
+      $self->_select_loop( $options );
+   }
+   $self->_cleanup;
+
+   return ! $self->full_result;
+}
+
+=pod
+
+=item result
+
+   $h->result;
+
+Returns the first non-zero result code (ie $? >> 8).  See L</full_result> to 
+get the $? value for a child process.
+
+To get the result of a particular child, do:
+
+   $h->result( 0 );  # first child's $? >> 8
+   $h->result( 1 );  # second child
+
+or
+
+   ($h->results)[0]
+   ($h->results)[1]
+
+Returns undef if no child processes were spawned and no child number was
+specified.  Throws an exception if an out-of-range child number is passed.
+
+=cut
+
+sub _assert_finished {
+   my IPC::Run $self = $_[0];
+
+   croak "Harness not run" unless $self->{STATE} >= _finished;
+   croak "Harness not finished running" unless $self->{STATE} == _finished;
+}
+
+
+sub result {
+   &_assert_finished;
+   my IPC::Run $self = shift;
+   
+   if ( @_ ) {
+      my ( $which ) = @_;
+      croak(
+         "Only ",
+         scalar( @{$self->{KIDS}} ),
+         " child processes, no process $which"
+      )
+         unless $which >= 0 && $which <= $#{$self->{KIDS}};
+      return $self->{KIDS}->[$which]->{RESULT} >> 8;
+   }
+   else {
+      return undef unless @{$self->{KIDS}};
+      for ( @{$self->{KIDS}} ) {
+         return $_->{RESULT} >> 8 if $_->{RESULT} >> 8;
+      }
+   }
+}
+
+=pod
+
+=item results
+
+Returns a list of child exit values.  See L</full_results> if you want to
+know if a signal killed the child.
+
+Throws an exception if the harness is not in a finished state.
+=cut
+
+sub results {
+   &_assert_finished;
+   my IPC::Run $self = shift;
+
+   # we add 0 here to stop warnings associated with "unknown result, unknown PID"
+   return map { (0+$_->{RESULT}) >> 8 } @{$self->{KIDS}};
+}
+
+=pod
+
+=item full_result
+
+   $h->full_result;
+
+Returns the first non-zero $?.  See L</result> to get the first $? >> 8 
+value for a child process.
+
+To get the result of a particular child, do:
+
+   $h->full_result( 0 );  # first child's $? >> 8
+   $h->full_result( 1 );  # second child
+
+or
+
+   ($h->full_results)[0]
+   ($h->full_results)[1]
+
+Returns undef if no child processes were spawned and no child number was
+specified.  Throws an exception if an out-of-range child number is passed.
+
+=cut
+
+sub full_result {
+   goto &result if @_ > 1;
+   &_assert_finished;
+
+   my IPC::Run $self = shift;
+
+   return undef unless @{$self->{KIDS}};
+   for ( @{$self->{KIDS}} ) {
+      return $_->{RESULT} if $_->{RESULT};
+   }
+}
+
+=pod
+
+=item full_results
+
+Returns a list of child exit values as returned by C<wait>.  See L</results>
+if you don't care about coredumps or signals.
+
+Throws an exception if the harness is not in a finished state.
+=cut
+
+sub full_results {
+   &_assert_finished;
+   my IPC::Run $self = shift;
+
+   croak "Harness not run" unless $self->{STATE} >= _finished;
+   croak "Harness not finished running" unless $self->{STATE} == _finished;
+
+   return map $_->{RESULT}, @{$self->{KIDS}};
+}
+
+
+##
+## Filter Scaffolding
+##
+use vars (
+   '$filter_op',        ## The op running a filter chain right now
+   '$filter_num',       ## Which filter is being run right now.
+);
+
+##
+## A few filters and filter constructors
+##
+
+=pod
+
+=back
+
+=back
+
+=head1 FILTERS
+
+These filters are used to modify input our output between a child
+process and a scalar or subroutine endpoint.
+
+=over
+
+=item binary
+
+   run \@cmd, ">", binary, \$out;
+   run \@cmd, ">", binary, \$out;  ## Any TRUE value to enable
+   run \@cmd, ">", binary 0, \$out;  ## Any FALSE value to disable
+
+This is a constructor for a "binmode" "filter" that tells IPC::Run to keep
+the carriage returns that would ordinarily be edited out for you (binmode
+is usually off).  This is not a real filter, but an option masquerading as
+a filter.
+
+It's not named "binmode" because you're likely to want to call Perl's binmode
+in programs that are piping binary data around.
+
+=cut
+
+sub binary(;$) {
+   my $enable = @_ ? shift : 1;
+   return bless sub { $enable }, "IPC::Run::binmode_pseudo_filter";
+}
+
+=pod
+
+=item new_chunker
+
+This breaks a stream of data in to chunks, based on an optional
+scalar or regular expression parameter.  The default is the Perl
+input record separator in $/, which is a newline be default.
+
+   run \@cmd, '>', new_chunker, \&lines_handler;
+   run \@cmd, '>', new_chunker( "\r\n" ), \&lines_handler;
+
+Because this uses $/ by default, you should always pass in a parameter
+if you are worried about other code (modules, etc) modifying $/.
+
+If this filter is last in a filter chain that dumps in to a scalar,
+the scalar must be set to '' before a new chunk will be written to it.
+
+As an example of how a filter like this can be written, here's a
+chunker that splits on newlines:
+
+   sub line_splitter {
+      my ( $in_ref, $out_ref ) = @_;
+
+      return 0 if length $$out_ref;
+
+      return input_avail && do {
+         while (1) {
+            if ( $$in_ref =~ s/\A(.*?\n)// ) {
+               $$out_ref .= $1;
+               return 1;
+            }
+            my $hmm = get_more_input;
+            unless ( defined $hmm ) {
+               $$out_ref = $$in_ref;
+               $$in_ref = '';
+               return length $$out_ref ? 1 : 0;
+            }
+            return 0 if $hmm eq 0;
+         }
+      }
+   };
+
+=cut
+
+sub new_chunker(;$) {
+   my ( $re ) = @_;
+   $re = $/ if _empty $re;
+   $re = quotemeta( $re ) unless ref $re eq 'Regexp';
+   $re = qr/\A(.*?$re)/s;
+
+   return sub {
+      my ( $in_ref, $out_ref ) = @_;
+
+      return 0 if length $$out_ref;
+
+      return input_avail && do {
+         while (1) {
+            if ( $$in_ref =~ s/$re// ) {
+               $$out_ref .= $1;
+               return 1;
+            }
+            my $hmm = get_more_input;
+            unless ( defined $hmm ) {
+               $$out_ref = $$in_ref;
+               $$in_ref = '';
+               return length $$out_ref ? 1 : 0;
+            }
+            return 0 if $hmm eq 0;
+         }
+      }
+   };
+}
+
+=pod
+
+=item new_appender
+
+This appends a fixed string to each chunk of data read from the source
+scalar or sub.  This might be useful if you're writing commands to a
+child process that always must end in a fixed string, like "\n":
+
+   run( \@cmd,
+      '<', new_appender( "\n" ), \&commands,
+   );
+
+Here's a typical filter sub that might be created by new_appender():
+
+   sub newline_appender {
+      my ( $in_ref, $out_ref ) = @_;
+
+      return input_avail && do {
+         $$out_ref = join( '', $$out_ref, $$in_ref, "\n" );
+         $$in_ref = '';
+         1;
+      }
+   };
+
+=cut
+
+sub new_appender($) {
+   my ( $suffix ) = @_;
+   croak "\$suffix undefined" unless defined $suffix;
+
+   return sub {
+      my ( $in_ref, $out_ref ) = @_;
+
+      return input_avail && do {
+         $$out_ref = join( '', $$out_ref, $$in_ref, $suffix );
+         $$in_ref = '';
+         1;
+      }
+   };
+}
+
+=item new_string_source
+
+TODO: Needs confirmation. Was previously undocumented. in this module.
+
+This is a filter which is exportable. Returns a sub which appends the data passed in to the output buffer and returns 1 if data was appended. 0 if it was an empty string and undef if no data was passed. 
+
+NOTE: Any additional variables passed to new_string_source will be passed to the sub every time it's called and appended to the output. 
+
+=cut
+
+
+sub new_string_source {
+   my $ref;
+   if ( @_ > 1 ) {
+      $ref = [ @_ ],
+   }
+   else {
+      $ref = shift;
+   }
+
+   return ref $ref eq 'SCALAR'
+      ? sub {
+         my ( $in_ref, $out_ref ) = @_;
+
+         return defined $$ref
+            ? do {
+               $$out_ref .= $$ref;
+               my $r = length $$ref ? 1 : 0;
+               $$ref = undef;
+               $r;
+            }
+            : undef
+      }
+      : sub {
+         my ( $in_ref, $out_ref ) = @_;
+
+         return @$ref
+            ? do {
+               my $s = shift @$ref;
+               $$out_ref .= $s;
+               length $s ? 1 : 0;
+            }
+            : undef;
+      }
+}
+
+=item new_string_sink
+
+TODO: Needs confirmation. Was previously undocumented.
+
+This is a filter which is exportable. Returns a sub which pops the data out of the input stream and pushes it onto the string.
+
+=cut
+
+sub new_string_sink {
+   my ( $string_ref ) = @_;
+
+   return sub {
+      my ( $in_ref, $out_ref ) = @_;
+
+      return input_avail && do {
+         $$string_ref .= $$in_ref;
+         $$in_ref = '';
+         1;
+      }
+   };
+}
+
+
+#=item timeout
+#
+#This function defines a time interval, starting from when start() is
+#called, or when timeout() is called.  If all processes have not finished
+#by the end of the timeout period, then a "process timed out" exception
+#is thrown.
+#
+#The time interval may be passed in seconds, or as an end time in
+#"HH:MM:SS" format (any non-digit other than '.' may be used as
+#spacing and punctuation).  This is probably best shown by example:
+#
+#   $h->timeout( $val );
+#
+#   $val                     Effect
+#   ======================== =====================================
+#   undef                    Timeout timer disabled
+#   ''                       Almost immediate timeout
+#   0                        Almost immediate timeout
+#   0.000001                 timeout > 0.0000001 seconds
+#   30                       timeout > 30 seconds
+#   30.0000001               timeout > 30 seconds
+#   10:30                    timeout > 10 minutes, 30 seconds
+#
+#Timeouts are currently evaluated with a 1 second resolution, though
+#this may change in the future.  This means that setting
+#timeout($h,1) will cause a pokey child to be aborted sometime after
+#one second has elapsed and typically before two seconds have elapsed.
+#
+#This sub does not check whether or not the timeout has expired already.
+#
+#Returns the number of seconds set as the timeout (this does not change
+#as time passes, unless you call timeout( val ) again).
+#
+#The timeout does not include the time needed to fork() or spawn()
+#the child processes, though some setup time for the child processes can
+#included.  It also does not include the length of time it takes for
+#the children to exit after they've closed all their pipes to the
+#parent process.
+#
+#=cut
+#
+#sub timeout {
+#   my IPC::Run $self = shift;
+#
+#   if ( @_ ) {
+#      ( $self->{TIMEOUT} ) = @_;
+#      $self->{TIMEOUT_END} = undef;
+#      if ( defined $self->{TIMEOUT} ) {
+#       if ( $self->{TIMEOUT} =~ /[^\d.]/ ) {
+#          my @f = split( /[^\d\.]+/i, $self->{TIMEOUT} );
+#          unshift @f, 0 while @f < 3;
+#          $self->{TIMEOUT} = (($f[0]*60)+$f[1])*60+$f[2];
+#       }
+#       elsif ( $self->{TIMEOUT} =~ /^(\d*)(?:\.(\d*))/ ) {
+#          $self->{TIMEOUT} = $1 + 1;
+#       }
+#       $self->_calc_timeout_end if $self->{STATE} >= _started;
+#      }
+#   }
+#   return $self->{TIMEOUT};
+#}
+#
+#
+#sub _calc_timeout_end {
+#   my IPC::Run $self = shift;
+#
+#   $self->{TIMEOUT_END} = defined $self->{TIMEOUT} 
+#      ? time + $self->{TIMEOUT}
+#      : undef;
+#
+#   ## We add a second because we might be at the very end of the current
+#   ## second, and we want to guarantee that we don't have a timeout even
+#   ## one second less then the timeout period.
+#   ++$self->{TIMEOUT_END} if $self->{TIMEOUT};
+#}
+
+=pod
+
+=item io
+
+Takes a filename or filehandle, a redirection operator, optional filters,
+and a source or destination (depends on the redirection operator).  Returns
+an IPC::Run::IO object suitable for harness()ing (including via start()
+or run()).
+
+This is shorthand for 
+
+
+   require IPC::Run::IO;
+
+      ... IPC::Run::IO->new(...) ...
+
+=cut
+
+sub io {
+   require IPC::Run::IO;
+   IPC::Run::IO->new( @_ );
+}
+
+=pod
+
+=item timer
+
+   $h = start( \@cmd, \$in, \$out, $t = timer( 5 ) );
+
+   pump $h until $out =~ /expected stuff/ || $t->is_expired;
+
+Instantiates a non-fatal timer.  pump() returns once each time a timer
+expires.  Has no direct effect on run(), but you can pass a subroutine
+to fire when the timer expires. 
+
+See L</timeout> for building timers that throw exceptions on
+expiration.
+
+See L<IPC::Run::Timer/timer> for details.
+
+=cut
+
+# Doing the prototype suppresses 'only used once' on older perls.
+sub timer;
+*timer = \&IPC::Run::Timer::timer;
+
+=pod
+
+=item timeout
+
+   $h = start( \@cmd, \$in, \$out, $t = timeout( 5 ) );
+
+   pump $h until $out =~ /expected stuff/;
+
+Instantiates a timer that throws an exception when it expires.
+If you don't provide an exception, a default exception that matches
+/^IPC::Run: .*timed out/ is thrown by default.  You can pass in your own
+exception scalar or reference:
+
+   $h = start(
+      \@cmd, \$in, \$out,
+      $t = timeout( 5, exception => 'slowpoke' ),
+   );
+
+or set the name used in debugging message and in the default exception
+string:
+
+   $h = start(
+      \@cmd, \$in, \$out,
+      timeout( 50, name => 'process timer' ),
+      $stall_timer = timeout( 5, name => 'stall timer' ),
+   );
+
+   pump $h until $out =~ /started/;
+
+   $in = 'command 1';
+   $stall_timer->start;
+   pump $h until $out =~ /command 1 finished/;
+
+   $in = 'command 2';
+   $stall_timer->start;
+   pump $h until $out =~ /command 2 finished/;
+
+   $in = 'very slow command 3';
+   $stall_timer->start( 10 );
+   pump $h until $out =~ /command 3 finished/;
+
+   $stall_timer->start( 5 );
+   $in = 'command 4';
+   pump $h until $out =~ /command 4 finished/;
+
+   $stall_timer->reset; # Prevent restarting or expirng
+   finish $h;
+
+See L</timer> for building non-fatal timers.
+
+See L<IPC::Run::Timer/timer> for details.
+
+=cut
+
+# Doing the prototype suppresses 'only used once' on older perls.
+sub timeout;
+*timeout = \&IPC::Run::Timer::timeout;
+
+=pod
+
+=back
+
+=head1 FILTER IMPLEMENTATION FUNCTIONS
+
+These functions are for use from within filters.
+
+=over
+
+=item input_avail
+
+Returns TRUE if input is available.  If none is available, then 
+&get_more_input is called and its result is returned.
+
+This is usually used in preference to &get_more_input so that the
+calling filter removes all data from the $in_ref before more data
+gets read in to $in_ref.
+
+C<input_avail> is usually used as part of a return expression:
+
+   return input_avail && do {
+      ## process the input just gotten
+      1;
+   };
+
+This technique allows input_avail to return the undef or 0 that a
+filter normally returns when there's no input to process.  If a filter
+stores intermediate values, however, it will need to react to an
+undef:
+
+   my $got = input_avail;
+   if ( ! defined $got ) {
+      ## No more input ever, flush internal buffers to $out_ref
+   }
+   return $got unless $got;
+   ## Got some input, move as much as need be
+   return 1 if $added_to_out_ref;
+
+=cut
+
+sub input_avail() {
+   confess "Undefined FBUF ref for $filter_num+1"
+      unless defined $filter_op->{FBUFS}->[$filter_num+1];
+   length ${$filter_op->{FBUFS}->[$filter_num+1]} || get_more_input;
+}
+
+=pod
+
+=item get_more_input
+
+This is used to fetch more input in to the input variable.  It returns
+undef if there will never be any more input, 0 if there is none now,
+but there might be in the future, and TRUE if more input was gotten.
+
+C<get_more_input> is usually used as part of a return expression,
+see L</input_avail> for more information.
+
+=cut
+
+##
+## Filter implementation interface
+##
+sub get_more_input() {
+   ++$filter_num;
+   my $r = eval {
+      confess "get_more_input() called and no more filters in chain"
+         unless defined $filter_op->{FILTERS}->[$filter_num];
+      $filter_op->{FILTERS}->[$filter_num]->(
+         $filter_op->{FBUFS}->[$filter_num+1],
+         $filter_op->{FBUFS}->[$filter_num],
+      ); # if defined ${$filter_op->{FBUFS}->[$filter_num+1]};
+   };
+   --$filter_num;
+   die $@ if $@;
+   return $r;
+}
+
+1;
+
+=pod
+
+=back
+
+=head1 TODO
+
+These will be addressed as needed and as time allows.
+
+Stall timeout.
+
+Expose a list of child process objects.  When I do this,
+each child process is likely to be blessed into IPC::Run::Proc.
+
+$kid->abort(), $kid->kill(), $kid->signal( $num_or_name ).
+
+Write tests for /(full_)?results?/ subs.
+
+Currently, pump() and run() only work on systems where select() works on the
+filehandles returned by pipe().  This does *not* include ActiveState on Win32,
+although it does work on cygwin under Win32 (thought the tests whine a bit).
+I'd like to rectify that, suggestions and patches welcome.
+
+Likewise start() only fully works on fork()/exec() machines (well, just
+fork() if you only ever pass perl subs as subprocesses).  There's
+some scaffolding for calling Open3::spawn_with_handles(), but that's
+untested, and not that useful with limited select().
+
+Support for C<\@sub_cmd> as an argument to a command which
+gets replaced with /dev/fd or the name of a temporary file containing foo's
+output.  This is like <(sub_cmd ...) found in bash and csh (IIRC).
+
+Allow multiple harnesses to be combined as independent sets of processes
+in to one 'meta-harness'.
+
+Allow a harness to be passed in place of an \@cmd.  This would allow
+multiple harnesses to be aggregated.
+
+Ability to add external file descriptors w/ filter chains and endpoints.
+
+Ability to add timeouts and timing generators (i.e. repeating timeouts).
+
+High resolution timeouts.
+
+=head1 Win32 LIMITATIONS
+
+=over
+
+=item Fails on Win9X
+
+If you want Win9X support, you'll have to debug it or fund me because I
+don't use that system any more.  The Win32 subsysem has been extended to
+use temporary files in simple run() invocations and these may actually
+work on Win9X too, but I don't have time to work on it.
+
+=item May deadlock on Win2K (but not WinNT4 or WinXPPro)
+
+Spawning more than one subprocess on Win2K causes a deadlock I haven't
+figured out yet, but simple uses of run() often work.  Passes all tests
+on WinXPPro and WinNT.
+
+=item no support yet for <pty< and >pty>
+
+These are likely to be implemented as "<" and ">" with binmode on, not
+sure.
+
+=item no support for file descriptors higher than 2 (stderr)
+
+Win32 only allows passing explicit fds 0, 1, and 2.  If you really, really need to pass file handles, us Win32API:: GetOsFHandle() or ::FdGetOsFHandle() to
+get the integer handle and pass it to the child process using the command
+line, environment, stdin, intermediary file, or other IPC mechanism.  Then
+use that handle in the child (Win32API.pm provides ways to reconstitute
+Perl file handles from Win32 file handles).
+
+=item no support for subroutine subprocesses (CODE refs)
+
+Can't fork(), so the subroutines would have no context, and closures certainly
+have no meaning
+
+Perhaps with Win32 fork() emulation, this can be supported in a limited
+fashion, but there are other very serious problems with that: all parent
+fds get dup()ed in to the thread emulating the forked process, and that
+keeps the parent from being able to close all of the appropriate fds.
+
+=item no support for init => sub {} routines.
+
+Win32 processes are created from scratch, there is no way to do an init
+routine that will affect the running child.  Some limited support might
+be implemented one day, do chdir() and %ENV changes can be made.
+
+=item signals
+
+Win32 does not fully support signals.  signal() is likely to cause errors
+unless sending a signal that Perl emulates, and C<kill_kill()> is immediately
+fatal (there is no grace period).
+
+=item helper processes
+
+IPC::Run uses helper processes, one per redirected file, to adapt between the
+anonymous pipe connected to the child and the TCP socket connected to the
+parent.  This is a waste of resources and will change in the future to either
+use threads (instead of helper processes) or a WaitForMultipleObjects call
+(instead of select).  Please contact me if you can help with the
+WaitForMultipleObjects() approach; I haven't figured out how to get at it
+without C code.
+
+=item shutdown pause
+
+There seems to be a pause of up to 1 second between when a child program exits
+and the corresponding sockets indicate that they are closed in the parent.
+Not sure why.
+
+=item binmode
+
+binmode is not supported yet.  The underpinnings are implemented, just ask
+if you need it.
+
+=item IPC::Run::IO
+
+IPC::Run::IO objects can be used on Unix to read or write arbitrary files.  On
+Win32, they will need to use the same helper processes to adapt from
+non-select()able filehandles to select()able ones (or perhaps
+WaitForMultipleObjects() will work with them, not sure).
+
+=item startup race conditions
+
+There seems to be an occasional race condition between child process startup
+and pipe closings.  It seems like if the child is not fully created by the time
+CreateProcess returns and we close the TCP socket being handed to it, the
+parent socket can also get closed.  This is seen with the Win32 pumper
+applications, not the "real" child process being spawned.
+
+I assume this is because the kernel hasn't gotten around to incrementing the
+reference count on the child's end (since the child was slow in starting), so
+the parent's closing of the child end causes the socket to be closed, thus
+closing the parent socket.
+
+Being a race condition, it's hard to reproduce, but I encountered it while
+testing this code on a drive share to a samba box.  In this case, it takes
+t/run.t a long time to spawn it's chile processes (the parent hangs in the
+first select for several seconds until the child emits any debugging output).
+
+I have not seen it on local drives, and can't reproduce it at will,
+unfortunately.  The symptom is a "bad file descriptor in select()" error, and,
+by turning on debugging, it's possible to see that select() is being called on
+a no longer open file descriptor that was returned from the _socket() routine
+in Win32Helper.  There's a new confess() that checks for this ("PARENT_HANDLE
+no longer open"), but I haven't been able to reproduce it (typically).
+
+=back
+
+=head1 LIMITATIONS
+
+On Unix, requires a system that supports C<waitpid( $pid, WNOHANG )> so
+it can tell if a child process is still running.
+
+PTYs don't seem to be non-blocking on some versions of Solaris. Here's a
+test script contributed by Borislav Deianov <borislav@ensim.com> to see
+if you have the problem.  If it dies, you have the problem.
+
+   #!/usr/bin/perl
+
+   use IPC::Run qw(run);
+   use Fcntl;
+   use IO::Pty;
+
+   sub makecmd {
+       return ['perl', '-e', 
+               '<STDIN>, print "\n" x '.$_[0].'; while(<STDIN>){last if /end/}'];
+   }
+
+   #pipe R, W;
+   #fcntl(W, F_SETFL, O_NONBLOCK);
+   #while (syswrite(W, "\n", 1)) { $pipebuf++ };
+   #print "pipe buffer size is $pipebuf\n";
+   my $pipebuf=4096;
+   my $in = "\n" x ($pipebuf * 2) . "end\n";
+   my $out;
+
+   $SIG{ALRM} = sub { die "Never completed!\n" };
+
+   print "reading from scalar via pipe...";
+   alarm( 2 );
+   run(makecmd($pipebuf * 2), '<', \$in, '>', \$out);
+   alarm( 0 );
+   print "done\n";
+
+   print "reading from code via pipe... ";
+   alarm( 2 );
+   run(makecmd($pipebuf * 3), '<', sub { $t = $in; undef $in; $t}, '>', \$out);
+   alarm( 0 );
+   print "done\n";
+
+   $pty = IO::Pty->new();
+   $pty->blocking(0);
+   $slave = $pty->slave();
+   while ($pty->syswrite("\n", 1)) { $ptybuf++ };
+   print "pty buffer size is $ptybuf\n";
+   $in = "\n" x ($ptybuf * 3) . "end\n";
+
+   print "reading via pty... ";
+   alarm( 2 );
+   run(makecmd($ptybuf * 3), '<pty<', \$in, '>', \$out);
+   alarm(0);
+   print "done\n";
+
+No support for ';', '&&', '||', '{ ... }', etc: use perl's, since run()
+returns TRUE when the command exits with a 0 result code.
+
+Does not provide shell-like string interpolation.
+
+No support for C<cd>, C<setenv>, or C<export>: do these in an init() sub
+
+   run(
+      \cmd,
+         ...
+         init => sub {
+            chdir $dir or die $!;
+            $ENV{FOO}='BAR'
+         }
+   );
+
+Timeout calculation does not allow absolute times, or specification of
+days, months, etc.
+
+B<WARNING:> Function coprocesses (C<run \&foo, ...>) suffer from two
+limitations.  The first is that it is difficult to close all filehandles the
+child inherits from the parent, since there is no way to scan all open
+FILEHANDLEs in Perl and it both painful and a bit dangerous to close all open
+file descriptors with C<POSIX::close()>. Painful because we can't tell which
+fds are open at the POSIX level, either, so we'd have to scan all possible fds
+and close any that we don't want open (normally C<exec()> closes any
+non-inheritable but we don't C<exec()> for &sub processes.
+
+The second problem is that Perl's DESTROY subs and other on-exit cleanup gets
+run in the child process.  If objects are instantiated in the parent before the
+child is forked, the DESTROY will get run once in the parent and once in
+the child.  When coprocess subs exit, POSIX::exit is called to work around this,
+but it means that objects that are still referred to at that time are not
+cleaned up.  So setting package vars or closure vars to point to objects that
+rely on DESTROY to affect things outside the process (files, etc), will
+lead to bugs.
+
+I goofed on the syntax: "<pipe" vs. "<pty<" and ">filename" are both
+oddities.
+
+=head1 TODO
+
+=over
+
+=item Allow one harness to "adopt" another:
+
+   $new_h = harness \@cmd2;
+   $h->adopt( $new_h );
+
+=item Close all filehandles not explicitly marked to stay open.
+
+The problem with this one is that there's no good way to scan all open
+FILEHANDLEs in Perl, yet you don't want child processes inheriting handles
+willy-nilly.
+
+=back
+
+=head1 INSPIRATION
+
+Well, select() and waitpid() badly needed wrapping, and open3() isn't
+open-minded enough for me.
+
+The shell-like API inspired by a message Russ Allbery sent to perl5-porters,
+which included:
+
+   I've thought for some time that it would be
+   nice to have a module that could handle full Bourne shell pipe syntax
+   internally, with fork and exec, without ever invoking a shell.  Something
+   that you could give things like:
+
+   pipeopen (PIPE, [ qw/cat file/ ], '|', [ 'analyze', @args ], '>&3');
+
+Message ylln51p2b6.fsf@windlord.stanford.edu, on 2000/02/04.
+
+=head1 SUPPORT
+
+Bugs should always be submitted via the CPAN bug tracker
+
+L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=IPC-Run>
+
+For other issues, contact the maintainer (the first listed author)
+
+=head1 AUTHORS
+
+Adam Kennedy <adamk@cpan.org>
+
+Barrie Slaymaker <barries@slaysys.com>
+
+=head1 COPYRIGHT
+
+Some parts copyright 2008 - 2009 Adam Kennedy.
+
+Copyright 1999 Barrie Slaymaker.
+
+You may distribute under the terms of either the GNU General Public
+License or the Artistic License, as specified in the README file.
+
+=cut
diff --git a/tools/cmake/scripts/IPC/Run/Debug.pm b/tools/cmake/scripts/IPC/Run/Debug.pm
new file mode 100644 (file)
index 0000000..78b2fa4
--- /dev/null
@@ -0,0 +1,312 @@
+package IPC::Run::Debug;
+
+=pod
+
+=head1 NAME
+
+IPC::Run::Debug - debugging routines for IPC::Run
+
+=head1 SYNOPSIS
+
+   ##
+   ## Environment variable usage
+   ##
+   ## To force debugging off and shave a bit of CPU and memory
+   ## by compile-time optimizing away all debugging code in IPC::Run
+   ## (debug => ...) options to IPC::Run will be ignored.
+   export IPCRUNDEBUG=none
+
+   ## To force debugging on (levels are from 0..10)
+   export IPCRUNDEBUG=basic
+
+   ## Leave unset or set to "" to compile in debugging support and
+   ## allow runtime control of it using the debug option.
+
+=head1 DESCRIPTION
+
+Controls IPC::Run debugging.  Debugging levels are now set by using words,
+but the numbers shown are still supported for backwards compatibility:
+
+   0  none         disabled (special, see below)
+   1  basic        what's running
+   2  data         what's being sent/recieved
+   3  details      what's going on in more detail
+   4  gory         way too much detail for most uses
+   10 all          use this when submitting bug reports
+      noopts       optimizations forbidden due to inherited STDIN
+
+The C<none> level is special when the environment variable IPCRUNDEBUG
+is set to this the first time IPC::Run::Debug is loaded: it prevents
+the debugging code from being compiled in to the remaining IPC::Run modules,
+saving a bit of cpu.
+
+To do this in a script, here's a way that allows it to be overridden:
+
+   BEGIN {
+      unless ( defined $ENV{IPCRUNDEBUG} ) {
+        eval 'local $ENV{IPCRUNDEBUG} = "none"; require IPC::Run::Debug"'
+           or die $@;
+      }
+   }
+
+This should force IPC::Run to not be debuggable unless somebody sets
+the IPCRUNDEBUG flag; modify this formula to grep @ARGV if need be:
+
+   BEGIN {
+      unless ( grep /^--debug/, @ARGV ) {
+        eval 'local $ENV{IPCRUNDEBUG} = "none"; require IPC::Run::Debug"'
+        or die $@;
+   }
+
+Both of those are untested.
+
+=cut
+
+## We use @EXPORT for the end user's convenience: there's only one function
+## exported, it's homonymous with the module, it's an unusual name, and
+## it can be suppressed by "use IPC::Run ();".
+
+use strict;
+use Exporter;
+use vars qw{$VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS};
+BEGIN {
+       $VERSION = '0.90';
+       @ISA     = qw( Exporter );
+       @EXPORT  = qw(
+               _debug
+               _debug_desc_fd
+               _debugging
+               _debugging_data
+               _debugging_details
+               _debugging_gory_details
+               _debugging_not_optimized
+               _set_child_debug_name
+       );
+       
+       @EXPORT_OK = qw(
+               _debug_init
+               _debugging_level
+               _map_fds
+       );
+       %EXPORT_TAGS = (
+               default => \@EXPORT,
+               all     => [ @EXPORT, @EXPORT_OK ],
+       );
+}
+
+my $disable_debugging =
+   defined $ENV{IPCRUNDEBUG}
+   && (
+      ! $ENV{IPCRUNDEBUG}
+      || lc $ENV{IPCRUNDEBUG} eq "none"
+   );
+
+eval( $disable_debugging ? <<'STUBS' : <<'SUBS' ) or die $@;
+sub _map_fds()                 { "" }
+sub _debug                     {}
+sub _debug_desc_fd             {}
+sub _debug_init                {}
+sub _set_child_debug_name      {}
+sub _debugging()               { 0 }
+sub _debugging_level()         { 0 }
+sub _debugging_data()          { 0 }
+sub _debugging_details()       { 0 }
+sub _debugging_gory_details()  { 0 }
+sub _debugging_not_optimized() { 0 }
+
+1;
+STUBS
+
+use POSIX;
+
+sub _map_fds {
+   my $map = '';
+   my $digit = 0;
+   my $in_use;
+   my $dummy;
+   for my $fd (0..63) {
+      ## I'd like a quicker way (less user, cpu & expecially sys and kernal
+      ## calls) to detect open file descriptors.  Let me know...
+      ## Hmmm, could do a 0 length read and check for bad file descriptor...
+      ## but that segfaults on Win32
+      my $test_fd = POSIX::dup( $fd );
+      $in_use = defined $test_fd;
+      POSIX::close $test_fd if $in_use;
+      $map .= $in_use ? $digit : '-';
+      $digit = 0 if ++$digit > 9;
+   }
+   warn "No fds open???" unless $map =~ /\d/;
+   $map =~ s/(.{1,12})-*$/$1/;
+   return $map;
+}
+
+use vars qw( $parent_pid );
+
+$parent_pid = $$;
+
+## TODO: move debugging to it's own module and make it compile-time
+## optimizable.
+
+## Give kid process debugging nice names
+my $debug_name;
+
+sub _set_child_debug_name {
+   $debug_name = shift;
+}
+
+## There's a bit of hackery going on here.
+##
+## We want to have any code anywhere be able to emit
+## debugging statements without knowing what harness the code is
+## being called in/from, since we'd need to pass a harness around to
+## everything.
+##
+## Thus, $cur_self was born.
+#
+my %debug_levels = (
+   none    => 0,
+   basic   => 1,
+   data    => 2,
+   details => 3,
+   gore           => 4,
+   gory_details   => 4,
+   "gory details" => 4,
+   gory           => 4,
+   gorydetails    => 4,
+   all     => 10,
+   notopt  => 0,
+);
+
+my $warned;
+
+sub _debugging_level() {
+   my $level = 0;
+
+   $level = $IPC::Run::cur_self->{debug} || 0
+      if $IPC::Run::cur_self
+         && ( $IPC::Run::cur_self->{debug} || 0 ) >= $level;
+
+   if ( defined $ENV{IPCRUNDEBUG} ) {
+      my $v = $ENV{IPCRUNDEBUG};
+      $v = $debug_levels{lc $v} if $v =~ /[a-zA-Z]/;
+      unless ( defined $v ) {
+        $warned ||= warn "Unknown debug level $ENV{IPCRUNDEBUG}, assuming 'basic' (1)\n";
+        $v = 1;
+      }
+      $level = $v if $v > $level;
+   }
+   return $level;
+}
+
+sub _debugging_atleast($) {
+   my $min_level = shift || 1;
+
+   my $level = _debugging_level;
+   
+   return $level >= $min_level ? $level : 0;
+}
+
+sub _debugging()               { _debugging_atleast 1 }
+sub _debugging_data()          { _debugging_atleast 2 }
+sub _debugging_details()       { _debugging_atleast 3 }
+sub _debugging_gory_details()  { _debugging_atleast 4 }
+sub _debugging_not_optimized() { ( $ENV{IPCRUNDEBUG} || "" ) eq "notopt" }
+
+sub _debug_init {
+   ## This routine is called only in spawned children to fake out the
+   ## debug routines so they'll emit debugging info.
+   $IPC::Run::cur_self = {};
+   (  $parent_pid,
+      $^T, 
+      $IPC::Run::cur_self->{debug}, 
+      $IPC::Run::cur_self->{DEBUG_FD}, 
+      $debug_name 
+   ) = @_;
+}
+
+
+sub _debug {
+#   return unless _debugging || _debugging_not_optimized;
+
+   my $fd = defined &IPC::Run::_debug_fd
+      ? IPC::Run::_debug_fd()
+      : fileno STDERR;
+
+   my $s;
+   my $debug_id;
+   $debug_id = join( 
+      " ",
+      join(
+         "",
+         defined $IPC::Run::cur_self ? "#$IPC::Run::cur_self->{ID}" : (),
+         "($$)",
+      ),
+      defined $debug_name && length $debug_name ? $debug_name        : (),
+   );
+   my $prefix = join(
+      "",
+      "IPC::Run",
+      sprintf( " %04d", time - $^T ),
+      ( _debugging_details ? ( " ", _map_fds ) : () ),
+      length $debug_id ? ( " [", $debug_id, "]" ) : (),
+      ": ",
+   );
+
+   my $msg = join( '', map defined $_ ? $_ : "<undef>", @_ );
+   chomp $msg;
+   $msg =~ s{^}{$prefix}gm;
+   $msg .= "\n";
+   POSIX::write( $fd, $msg, length $msg );
+}
+
+
+my @fd_descs = ( 'stdin', 'stdout', 'stderr' );
+
+sub _debug_desc_fd {
+   return unless _debugging;
+   my $text = shift;
+   my $op = pop;
+   my $kid = $_[0];
+
+Carp::carp join " ", caller(0), $text, $op  if defined $op  && UNIVERSAL::isa( $op, "IO::Pty" );
+
+   _debug(
+      $text,
+      ' ',
+      ( defined $op->{FD}
+         ? $op->{FD} < 3
+            ? ( $fd_descs[$op->{FD}] )
+            : ( 'fd ', $op->{FD} )
+         : $op->{FD}
+      ),
+      ( defined $op->{KFD}
+         ? (
+            ' (kid',
+            ( defined $kid ? ( ' ', $kid->{NUM}, ) : () ),
+            "'s ",
+            ( $op->{KFD} < 3
+               ? $fd_descs[$op->{KFD}]
+               : defined $kid
+                  && defined $kid->{DEBUG_FD}
+                  && $op->{KFD} == $kid->{DEBUG_FD}
+                  ? ( 'debug (', $op->{KFD}, ')' )
+                  : ( 'fd ', $op->{KFD} )
+            ),
+            ')',
+         )
+         : ()
+      ),
+   );
+}
+
+1;
+
+SUBS
+
+=pod
+
+=head1 AUTHOR
+
+Barrie Slaymaker <barries@slaysys.com>, with numerous suggestions by p5p.
+
+=cut
diff --git a/tools/cmake/scripts/IPC/Run/IO.pm b/tools/cmake/scripts/IPC/Run/IO.pm
new file mode 100644 (file)
index 0000000..dcfb4d1
--- /dev/null
@@ -0,0 +1,584 @@
+package IPC::Run::IO;
+
+=head1 NAME
+
+IPC::Run::IO -- I/O channels for IPC::Run.
+
+=head1 SYNOPSIS
+
+B<NOT IMPLEMENTED YET ON Win32! Win32 does not allow select() on
+normal file descriptors; IPC::RUN::IO needs to use IPC::Run::Win32Helper
+to do this.>
+
+   use IPC::Run qw( io );
+
+   ## The sense of '>' and '<' is opposite of perl's open(),
+   ## but agrees with IPC::Run.
+   $io = io( "filename", '>',  \$recv );
+   $io = io( "filename", 'r',  \$recv );
+
+   ## Append to $recv:
+   $io = io( "filename", '>>', \$recv );
+   $io = io( "filename", 'ra', \$recv );
+
+   $io = io( "filename", '<',  \$send );
+   $io = io( "filename", 'w',  \$send );
+
+   $io = io( "filename", '<<', \$send );
+   $io = io( "filename", 'wa', \$send );
+
+   ## Handles / IO objects that the caller opens:
+   $io = io( \*HANDLE,   '<',  \$send );
+
+   $f = IO::Handle->new( ... ); # Any subclass of IO::Handle
+   $io = io( $f, '<', \$send );
+
+   require IPC::Run::IO;
+   $io = IPC::Run::IO->new( ... );
+
+   ## Then run(), harness(), or start():
+   run $io, ...;
+
+   ## You can, of course, use io() or IPC::Run::IO->new() as an
+   ## argument to run(), harness, or start():
+   run io( ... );
+
+=head1 DESCRIPTION
+
+This class and module allows filehandles and filenames to be harnessed for
+I/O when used IPC::Run, independent of anything else IPC::Run is doing
+(except that errors & exceptions can affect all things that IPC::Run is
+doing).
+
+=head1 SUBCLASSING
+
+INCOMPATIBLE CHANGE: due to the awkwardness introduced in ripping pseudohashes
+out of Perl, this class I<no longer> uses the fields pragma.
+
+=cut
+
+## This class is also used internally by IPC::Run in a very intimate way,
+## since this is a partial factoring of code from IPC::Run plus some code
+## needed to do standalone channels.  This factoring process will continue
+## at some point.  Don't know how far how fast.
+
+use strict;
+use Carp;
+use Fcntl;
+use Symbol;
+
+use IPC::Run::Debug;
+use IPC::Run qw( Win32_MODE );
+
+use vars qw{$VERSION};
+BEGIN {
+       $VERSION = '0.90';
+       if ( Win32_MODE ) {
+               eval "use IPC::Run::Win32Helper; require IPC::Run::Win32IO; 1"
+               or ( $@ && die ) or die "$!";
+       }
+}
+
+sub _empty($);
+*_empty = \&IPC::Run::_empty;
+
+=head1 SUBROUTINES
+
+=over 4
+
+=item new
+
+I think it takes >> or << along with some other data.
+
+TODO: Needs more thorough documentation. Patches welcome.
+
+=cut
+
+sub new {
+   my $class = shift;
+   $class = ref $class || $class;
+
+   my ( $external, $type, $internal ) = ( shift, shift, pop );
+
+   croak "$class: '$_' is not a valid I/O operator"
+      unless $type =~ /^(?:<<?|>>?)$/;
+
+   my IPC::Run::IO $self = $class->_new_internal(
+      $type, undef, undef, $internal, undef, @_
+   );
+
+   if ( ! ref $external ) {
+      $self->{FILENAME} = $external;
+   }
+   elsif ( ref eq 'GLOB' || UNIVERSAL::isa( $external, 'IO::Handle' ) ) {
+      $self->{HANDLE} = $external;
+      $self->{DONT_CLOSE} = 1;
+   }
+   else {
+      croak "$class: cannot accept " . ref( $external ) . " to do I/O with";
+   }
+
+   return $self;
+}
+
+
+## IPC::Run uses this ctor, since it preparses things and needs more
+## smarts.
+sub _new_internal {
+   my $class = shift;
+   $class = ref $class || $class;
+
+   $class = "IPC::Run::Win32IO"
+      if Win32_MODE && $class eq "IPC::Run::IO";
+
+   my IPC::Run::IO $self;
+   $self = bless {}, $class;
+
+   my ( $type, $kfd, $pty_id, $internal, $binmode, @filters ) = @_;
+
+   # Older perls (<=5.00503, at least) don't do list assign to
+   # psuedo-hashes well.
+   $self->{TYPE}    = $type;
+   $self->{KFD}     = $kfd;
+   $self->{PTY_ID}  = $pty_id;
+   $self->binmode( $binmode );
+   $self->{FILTERS} = [ @filters ];
+
+   ## Add an adapter to the end of the filter chain (which is usually just the
+   ## read/writer sub pushed by IPC::Run) to the DEST or SOURCE, if need be.
+   if ( $self->op =~ />/ ) {
+      croak "'$_' missing a destination" if _empty $internal;
+      $self->{DEST} = $internal;
+      if ( UNIVERSAL::isa( $self->{DEST}, 'CODE' ) ) {
+         ## Put a filter on the end of the filter chain to pass the
+         ## output on to the CODE ref.  For SCALAR refs, the last
+         ## filter in the chain writes directly to the scalar itself.  See
+         ## _init_filters().  For CODE refs, however, we need to adapt from
+         ## the SCALAR to calling the CODE.
+         unshift( 
+            @{$self->{FILTERS}},
+            sub {
+               my ( $in_ref ) = @_;
+
+               return IPC::Run::input_avail() && do {
+                 $self->{DEST}->( $$in_ref );
+                 $$in_ref = '';
+                 1;
+               }
+            }
+         );
+      }
+   }
+   else {
+      croak "'$_' missing a source" if _empty $internal;
+      $self->{SOURCE} = $internal;
+      if ( UNIVERSAL::isa( $internal, 'CODE' ) ) {
+         push(
+            @{$self->{FILTERS}},
+            sub {
+               my ( $in_ref, $out_ref ) = @_;
+               return 0 if length $$out_ref;
+
+               return undef
+                 if $self->{SOURCE_EMPTY};
+
+               my $in = $internal->();
+               unless ( defined $in ) {
+                 $self->{SOURCE_EMPTY} = 1;
+                 return undef 
+               }
+               return 0 unless length $in;
+               $$out_ref = $in;
+
+               return 1;
+            }
+         );
+      }
+      elsif ( UNIVERSAL::isa( $internal, 'SCALAR' ) ) {
+         push(
+            @{$self->{FILTERS}},
+            sub {
+               my ( $in_ref, $out_ref ) = @_;
+               return 0 if length $$out_ref;
+
+               ## pump() clears auto_close_ins, finish() sets it.
+               return $self->{HARNESS}->{auto_close_ins} ? undef : 0
+                 if IPC::Run::_empty ${$self->{SOURCE}}
+                    || $self->{SOURCE_EMPTY};
+
+               $$out_ref = $$internal;
+               eval { $$internal = '' }
+                 if $self->{HARNESS}->{clear_ins};
+
+               $self->{SOURCE_EMPTY} = $self->{HARNESS}->{auto_close_ins};
+
+               return 1;
+            }
+         );
+      }
+   }
+
+   return $self;
+}
+
+=item filename
+
+Gets/sets the filename.  Returns the value after the name change, if
+any.
+
+=cut
+
+sub filename {
+   my IPC::Run::IO $self = shift;
+   $self->{FILENAME} = shift if @_;
+   return $self->{FILENAME};
+}
+
+=item init
+
+Does initialization required before this can be run.  This includes open()ing
+the file, if necessary, and clearing the destination scalar if necessary.
+
+=cut
+
+sub init {
+   my IPC::Run::IO $self = shift;
+
+   $self->{SOURCE_EMPTY} = 0;
+   ${$self->{DEST}} = ''
+      if $self->mode =~ /r/ && ref $self->{DEST} eq 'SCALAR';
+
+   $self->open if defined $self->filename;
+   $self->{FD} = $self->fileno;
+
+   if ( ! $self->{FILTERS} ) {
+      $self->{FBUFS} = undef;
+   }
+   else {
+      @{$self->{FBUFS}} = map {
+         my $s = "";
+         \$s;
+      } ( @{$self->{FILTERS}}, '' );
+
+      $self->{FBUFS}->[0] = $self->{DEST}
+         if $self->{DEST} && ref $self->{DEST} eq 'SCALAR';
+      push @{$self->{FBUFS}}, $self->{SOURCE};
+   }
+
+   return undef;
+}
+
+
+=item open
+
+If a filename was passed in, opens it.  Determines if the handle is open
+via fileno().  Throws an exception on error.
+
+=cut
+
+my %open_flags = (
+   '>'  => O_RDONLY,
+   '>>' => O_RDONLY,
+   '<'  => O_WRONLY | O_CREAT | O_TRUNC,
+   '<<' => O_WRONLY | O_CREAT | O_APPEND,
+);
+
+sub open {
+   my IPC::Run::IO $self = shift;
+
+   croak "IPC::Run::IO: Can't open() a file with no name"
+      unless defined $self->{FILENAME};
+   $self->{HANDLE} = gensym unless $self->{HANDLE};
+
+   _debug
+      "opening '", $self->filename, "' mode '", $self->mode, "'"
+   if _debugging_data;
+   sysopen(
+      $self->{HANDLE},
+      $self->filename,
+      $open_flags{$self->op},
+   ) or croak
+         "IPC::Run::IO: $! opening '$self->{FILENAME}', mode '" . $self->mode . "'";
+
+   return undef;
+}
+
+
+=item open_pipe
+
+If this is a redirection IO object, this opens the pipe in a platform
+independent manner.
+
+=cut
+
+sub _do_open {
+   my $self = shift;
+   my ( $child_debug_fd, $parent_handle ) = @_;
+
+
+   if ( $self->dir eq "<" ) {
+      ( $self->{TFD}, $self->{FD} ) = IPC::Run::_pipe_nb;
+      if ( $parent_handle ) {
+         CORE::open $parent_handle, ">&=$self->{FD}"
+            or croak "$! duping write end of pipe for caller";
+      }
+   }
+   else {
+      ( $self->{FD}, $self->{TFD} ) = IPC::Run::_pipe;
+      if ( $parent_handle ) {
+         CORE::open $parent_handle, "<&=$self->{FD}"
+            or croak "$! duping read end of pipe for caller";
+      }
+   }
+}
+
+sub open_pipe {
+   my IPC::Run::IO $self = shift;
+
+   ## Hmmm, Maybe allow named pipes one day.  But until then...
+   croak "IPC::Run::IO: Can't pipe() when a file name has been set"
+      if defined $self->{FILENAME};
+
+   $self->_do_open( @_ );
+
+   ## return ( child_fd, parent_fd )
+   return $self->dir eq "<"
+      ? ( $self->{TFD}, $self->{FD} )
+      : ( $self->{FD}, $self->{TFD} );
+}
+
+
+sub _cleanup { ## Called from Run.pm's _cleanup
+   my $self = shift;
+   undef $self->{FAKE_PIPE};
+}
+
+
+=item close
+
+Closes the handle.  Throws an exception on failure.
+
+
+=cut
+
+sub close {
+   my IPC::Run::IO $self = shift;
+
+   if ( defined $self->{HANDLE} ) {
+      close $self->{HANDLE}
+         or croak(  "IPC::Run::IO: $! closing "
+            . ( defined $self->{FILENAME}
+               ? "'$self->{FILENAME}'"
+               : "handle"
+            )
+         );
+   }
+   else {
+      IPC::Run::_close( $self->{FD} );
+   }
+
+   $self->{FD} = undef;
+
+   return undef;
+}
+
+=item fileno
+
+Returns the fileno of the handle.  Throws an exception on failure.
+
+
+=cut
+
+sub fileno {
+   my IPC::Run::IO $self = shift;
+
+   my $fd = fileno $self->{HANDLE};
+   croak(  "IPC::Run::IO: $! "
+         . ( defined $self->{FILENAME}
+            ? "'$self->{FILENAME}'"
+            : "handle"
+         )
+      ) unless defined $fd;
+
+   return $fd;
+}
+
+=item mode
+
+Returns the operator in terms of 'r', 'w', and 'a'.  There is a state
+'ra', unlike Perl's open(), which indicates that data read from the
+handle or file will be appended to the output if the output is a scalar.
+This is only meaningful if the output is a scalar, it has no effect if
+the output is a subroutine.
+
+The redirection operators can be a little confusing, so here's a reference
+table:
+
+   >      r      Read from handle in to process
+   <      w      Write from process out to handle
+   >>     ra     Read from handle in to process, appending it to existing
+                 data if the destination is a scalar.
+   <<     wa     Write from process out to handle, appending to existing
+                 data if IPC::Run::IO opened a named file.
+
+=cut
+
+sub mode {
+   my IPC::Run::IO $self = shift;
+
+   croak "IPC::Run::IO: unexpected arguments for mode(): @_" if @_;
+
+   ## TODO: Optimize this
+   return ( $self->{TYPE} =~ /</     ? 'w' : 'r' ) . 
+          ( $self->{TYPE} =~ /<<|>>/ ? 'a' : ''  );
+}
+
+
+=item op
+
+Returns the operation: '<', '>', '<<', '>>'.  See L</mode> if you want
+to spell these 'r', 'w', etc.
+
+=cut
+
+sub op {
+   my IPC::Run::IO $self = shift;
+
+   croak "IPC::Run::IO: unexpected arguments for op(): @_" if @_;
+
+   return $self->{TYPE};
+}
+
+=item binmode
+
+Sets/gets whether this pipe is in binmode or not.  No effect off of Win32
+OSs, of course, and on Win32, no effect after the harness is start()ed.
+
+=cut
+
+sub binmode {
+   my IPC::Run::IO $self = shift;
+
+   $self->{BINMODE} = shift if @_;
+
+   return $self->{BINMODE};
+}
+
+
+=item dir
+
+Returns the first character of $self->op.  This is either "<" or ">".
+
+=cut
+
+sub dir {
+   my IPC::Run::IO $self = shift;
+
+   croak "IPC::Run::IO: unexpected arguments for dir(): @_" if @_;
+
+   return substr $self->{TYPE}, 0, 1;
+}
+
+
+##
+## Filter Scaffolding
+##
+#my $filter_op ;        ## The op running a filter chain right now
+#my $filter_num;        ## Which filter is being run right now.
+
+use vars (
+'$filter_op',        ## The op running a filter chain right now
+'$filter_num'        ## Which filter is being run right now.
+);
+
+sub _init_filters {
+   my IPC::Run::IO $self = shift;
+
+confess "\$self not an IPC::Run::IO" unless UNIVERSAL::isa( $self, "IPC::Run::IO" );
+   $self->{FBUFS} = [];
+
+   $self->{FBUFS}->[0] = $self->{DEST}
+      if $self->{DEST} && ref $self->{DEST} eq 'SCALAR';
+
+   return unless $self->{FILTERS} && @{$self->{FILTERS}};
+
+   push @{$self->{FBUFS}}, map {
+      my $s = "";
+      \$s;
+   } ( @{$self->{FILTERS}}, '' );
+
+   push @{$self->{FBUFS}}, $self->{SOURCE};
+}
+
+=item poll
+
+TODO: Needs confirmation that this is correct. Was previously undocumented.
+
+I believe this is polling the IO for new input and then returns undef if there will never be any more input, 0 if there is none now, but there might be in the future, and TRUE if more input was gotten.
+
+=cut
+
+sub poll {
+   my IPC::Run::IO $self = shift;
+   my ( $harness ) = @_;
+
+   if ( defined $self->{FD} ) {
+      my $d = $self->dir;
+      if ( $d eq "<" ) {
+         if ( vec $harness->{WOUT}, $self->{FD}, 1 ) {
+            _debug_desc_fd( "filtering data to", $self )
+               if _debugging_details;
+            return $self->_do_filters( $harness );
+         }
+      }
+      elsif ( $d eq ">" ) {
+         if ( vec $harness->{ROUT}, $self->{FD}, 1 ) {
+            _debug_desc_fd( "filtering data from", $self )
+               if _debugging_details;
+            return $self->_do_filters( $harness );
+         }
+      }
+   }
+   return 0;
+}
+
+
+sub _do_filters {
+   my IPC::Run::IO $self = shift;
+
+   ( $self->{HARNESS} ) = @_;
+
+   my ( $saved_op, $saved_num ) =($IPC::Run::filter_op,$IPC::Run::filter_num);
+   $IPC::Run::filter_op = $self;
+   $IPC::Run::filter_num = -1;
+   my $redos = 0;
+   my $r;
+   {
+          $@ = '';
+          $r = eval { IPC::Run::get_more_input(); };
+
+          # Detect Resource temporarily unavailable and re-try 200 times (2 seconds),  assuming select behaves (which it doesn't always? need ref)
+          if(($@||'') =~ $IPC::Run::_EAGAIN && $redos++ < 200) {
+              select(undef, undef, undef, 0.01);
+              redo;
+          }
+   }
+   ( $IPC::Run::filter_op, $IPC::Run::filter_num ) = ( $saved_op, $saved_num );
+   $self->{HARNESS} = undef;
+   die "ack ", $@ if $@;
+   return $r;
+}
+
+=back
+
+=head1 AUTHOR
+
+Barrie Slaymaker <barries@slaysys.com>
+
+=head1 TODO
+
+Implement bidirectionality.
+
+=cut
+
+1;
diff --git a/tools/cmake/scripts/IPC/Run/Timer.pm b/tools/cmake/scripts/IPC/Run/Timer.pm
new file mode 100644 (file)
index 0000000..6e4675e
--- /dev/null
@@ -0,0 +1,690 @@
+package IPC::Run::Timer;
+
+=pod
+
+=head1 NAME
+
+IPC::Run::Timer -- Timer channels for IPC::Run.
+
+=head1 SYNOPSIS
+
+   use IPC::Run qw( run  timer timeout );
+   ## or IPC::Run::Timer ( timer timeout );
+   ## or IPC::Run::Timer ( :all );
+
+   ## A non-fatal timer:
+   $t = timer( 5 ); # or...
+   $t = IO::Run::Timer->new( 5 );
+   run $t, ...;
+
+   ## A timeout (which is a timer that dies on expiry):
+   $t = timeout( 5 ); # or...
+   $t = IO::Run::Timer->new( 5, exception => "harness timed out" );
+
+=head1 DESCRIPTION
+
+This class and module allows timers and timeouts to be created for use
+by IPC::Run.  A timer simply expires when it's time is up.  A timeout
+is a timer that throws an exception when it expires.
+
+Timeouts are usually a bit simpler to use  than timers: they throw an
+exception on expiration so you don't need to check them:
+
+   ## Give @cmd 10 seconds to get started, then 5 seconds to respond
+   my $t = timeout( 10 );
+   $h = start(
+      \@cmd, \$in, \$out,
+      $t,
+   );
+   pump $h until $out =~ /prompt/;
+
+   $in = "some stimulus";
+   $out = '';
+   $t->time( 5 )
+   pump $h until $out =~ /expected response/;
+
+You do need to check timers:
+
+   ## Give @cmd 10 seconds to get started, then 5 seconds to respond
+   my $t = timer( 10 );
+   $h = start(
+      \@cmd, \$in, \$out,
+      $t,
+   );
+   pump $h until $t->is_expired || $out =~ /prompt/;
+
+   $in = "some stimulus";
+   $out = '';
+   $t->time( 5 )
+   pump $h until $out =~ /expected response/ || $t->is_expired;
+
+Timers and timeouts that are reset get started by start() and
+pump().  Timers change state only in pump().  Since run() and
+finish() both call pump(), they act like pump() with respect to
+timers.
+
+Timers and timeouts have three states: reset, running, and expired.
+Setting the timeout value resets the timer, as does calling
+the reset() method.  The start() method starts (or restarts) a
+timer with the most recently set time value, no matter what state
+it's in.
+
+=head2 Time values
+
+All time values are in seconds.  Times may be specified as integer or
+floating point seconds, optionally preceded by puncuation-separated
+days, hours, and minutes.\
+
+Examples:
+
+   1           1 second
+   1.1         1.1 seconds
+   60          60 seconds
+   1:0         1 minute
+   1:1         1 minute, 1 second
+   1:90        2 minutes, 30 seconds
+   1:2:3:4.5   1 day, 2 hours, 3 minutes, 4.5 seconds
+
+Absolute date/time strings are *not* accepted: year, month and
+day-of-month parsing is not available (patches welcome :-).
+
+=head2 Interval fudging
+
+When calculating an end time from a start time and an interval, IPC::Run::Timer
+instances add a little fudge factor.  This is to ensure that no time will
+expire before the interval is up.
+
+First a little background.  Time is sampled in discrete increments.  We'll
+call the
+exact moment that the reported time increments from one interval to the
+next a tick, and the interval between ticks as the time period.  Here's
+a diagram of three ticks and the periods between them:
+
+
+    -0-0-0-0-0-0-0-0-0-0-1-1-1-1-1-1-1-1-1-1-2-...
+    ^                   ^                   ^
+    |<--- period 0 ---->|<--- period 1 ---->|
+    |                   |                   |
+  tick 0              tick 1              tick 2
+
+To see why the fudge factor is necessary, consider what would happen
+when a timer with an interval of 1 second is started right at the end of
+period 0:
+
+
+    -0-0-0-0-0-0-0-0-0-0-1-1-1-1-1-1-1-1-1-1-2-...
+    ^                ^  ^                   ^
+    |                |  |                   |
+    |                |  |                   |
+  tick 0             |tick 1              tick 2
+                     |
+                 start $t
+
+Assuming that check() is called many times per period, then the timer
+is likely to expire just after tick 1, since the time reported will have
+lept from the value '0' to the value '1':
+
+    -0-0-0-0-0-0-0-0-0-0-1-1-1-1-1-1-1-1-1-1-2-...
+    ^                ^  ^   ^               ^
+    |                |  |   |               |
+    |                |  |   |               |
+  tick 0             |tick 1|             tick 2
+                     |      |
+                 start $t   |
+                           |
+                       check $t
+
+Adding a fudge of '1' in this example means that the timer is guaranteed
+not to expire before tick 2.
+
+The fudge is not added to an interval of '0'.
+
+This means that intervals guarantee a minimum interval.  Given that
+the process running perl may be suspended for some period of time, or that
+it gets busy doing something time-consuming, there are no other guarantees on
+how long it will take a timer to expire.
+
+=head1 SUBCLASSING
+
+INCOMPATIBLE CHANGE: Due to the awkwardness introduced by ripping
+pseudohashes out of Perl, this class I<no longer> uses the fields
+pragma.
+
+=head1 FUNCTIONS & METHODS
+
+=over
+
+=cut
+
+use strict;
+use Carp;
+use Fcntl;
+use Symbol;
+use Exporter;
+use vars qw( $VERSION @ISA @EXPORT_OK %EXPORT_TAGS );
+BEGIN {
+       $VERSION   = '0.90';
+       @ISA       = qw( Exporter );
+       @EXPORT_OK = qw(
+               check
+               end_time
+               exception
+               expire
+               interval
+               is_expired
+               is_reset
+               is_running
+               name
+               reset
+               start
+               timeout
+               timer
+       );
+
+       %EXPORT_TAGS = ( 'all' => \@EXPORT_OK );
+}
+
+require IPC::Run;
+use IPC::Run::Debug;
+
+##
+## Some helpers
+##
+my $resolution = 1;
+
+sub _parse_time {
+   for ( $_[0] ) {
+      return $_ unless defined $_;
+      return $_ if /^\d*(?:\.\d*)?$/;
+
+      my @f = reverse split( /[^\d\.]+/i );
+      croak "IPC::Run: invalid time string '$_'" unless @f <= 4;
+      my ( $s, $m, $h, $d ) = @f;
+      return
+      ( (
+                ( $d || 0 )   * 24
+              + ( $h || 0 ) ) * 60
+              + ( $m || 0 ) ) * 60
+               + ( $s || 0 );
+   }
+}
+
+sub _calc_end_time {
+   my IPC::Run::Timer $self = shift;
+   my $interval = $self->interval;
+   $interval += $resolution if $interval;
+   $self->end_time( $self->start_time + $interval );
+}
+
+
+=item timer
+
+A constructor function (not method) of IPC::Run::Timer instances:
+
+   $t = timer( 5 );
+   $t = timer( 5, name => 'stall timer', debug => 1 );
+
+   $t = timer;
+   $t->interval( 5 );
+
+   run ..., $t;
+   run ..., $t = timer( 5 );
+
+This convenience function is a shortened spelling of
+
+   IPC::Run::Timer->new( ... );
+   
+.  It returns a timer in the reset state with a given interval.
+
+If an exception is provided, it will be thrown when the timer notices that
+it has expired (in check()).  The name is for debugging usage, if you plan on
+having multiple timers around.  If no name is provided, a name like "timer #1"
+will be provided.
+
+=cut
+
+sub timer {
+   return IPC::Run::Timer->new( @_ );
+}
+
+
+=item timeout
+
+A constructor function (not method) of IPC::Run::Timer instances:
+
+   $t = timeout( 5 );
+   $t = timeout( 5, exception => "kablooey" );
+   $t = timeout( 5, name => "stall", exception => "kablooey" );
+
+   $t = timeout;
+   $t->interval( 5 );
+
+   run ..., $t;
+   run ..., $t = timeout( 5 );
+
+A This convenience function is a shortened spelling of 
+
+   IPC::Run::Timer->new( exception => "IPC::Run: timeout ...", ... );
+   
+.  It returns a timer in the reset state that will throw an
+exception when it expires.
+
+Takes the same parameters as L</timer>, any exception passed in overrides
+the default exception.
+
+=cut
+
+sub timeout {
+   my $t = IPC::Run::Timer->new( @_ );
+   $t->exception( "IPC::Run: timeout on " . $t->name )
+      unless defined $t->exception;
+   return $t;
+}
+
+
+=item new
+
+   IPC::Run::Timer->new()  ;
+   IPC::Run::Timer->new( 5 )  ;
+   IPC::Run::Timer->new( 5, exception => 'kablooey' )  ;
+
+Constructor.  See L</timer> for details.
+
+=cut
+
+my $timer_counter;
+
+
+sub new {
+   my $class = shift;
+   $class = ref $class || $class;
+
+   my IPC::Run::Timer $self = bless {}, $class;
+
+   $self->{STATE} = 0;
+   $self->{DEBUG} = 0;
+   $self->{NAME}  = "timer #" . ++$timer_counter;
+
+   while ( @_ ) {
+      my $arg = shift;
+      if ( $arg =~ /^(?:\d+[^\a\d]){0,3}\d*(?:\.\d*)?$/ ) {
+         $self->interval( $arg );
+      }
+      elsif ( $arg eq 'exception' ) {
+         $self->exception( shift );
+      }
+      elsif ( $arg eq 'name' ) {
+         $self->name( shift );
+      }
+      elsif ( $arg eq 'debug' ) {
+         $self->debug( shift );
+      }
+      else {
+         croak "IPC::Run: unexpected parameter '$arg'";
+      }
+   }
+
+   _debug $self->name . ' constructed'
+      if $self->{DEBUG} || _debugging_details;
+
+   return $self;
+}
+
+=item check
+
+   check $t;
+   check $t, $now;
+   $t->check;
+
+Checks to see if a timer has expired since the last check.  Has no effect
+on non-running timers.  This will throw an exception if one is defined.
+
+IPC::Run::pump() calls this routine for any timers in the harness.
+
+You may pass in a version of now, which is useful in case you have
+it lying around or you want to check several timers with a consistent
+concept of the current time.
+
+Returns the time left before end_time or 0 if end_time is no longer
+in the future or the timer is not running
+(unless, of course, check() expire()s the timer and this
+results in an exception being thrown).
+
+Returns undef if the timer is not running on entry, 0 if check() expires it,
+and the time left if it's left running.
+
+=cut
+
+sub check {
+   my IPC::Run::Timer $self = shift;
+   return undef if ! $self->is_running;
+   return 0     if  $self->is_expired;
+
+   my ( $now ) = @_;
+   $now = _parse_time( $now );
+   $now = time unless defined $now;
+
+   _debug(
+      "checking ", $self->name, " (end time ", $self->end_time, ") at ", $now 
+   ) if $self->{DEBUG} || _debugging_details;
+
+   my $left = $self->end_time - $now;
+   return $left if $left > 0;
+
+   $self->expire;
+   return 0;
+}
+
+
+=item debug
+
+Sets/gets the current setting of the debugging flag for this timer.  This
+has no effect if debugging is not enabled for the current harness.
+
+=cut
+
+
+sub debug {
+   my IPC::Run::Timer $self = shift;
+   $self->{DEBUG} = shift if @_;
+   return $self->{DEBUG};
+}
+
+
+=item end_time
+
+   $et = $t->end_time;
+   $et = end_time $t;
+
+   $t->end_time( time + 10 );
+
+Returns the time when this timer will or did expire.  Even if this time is
+in the past, the timer may not be expired, since check() may not have been
+called yet.
+
+Note that this end_time is not start_time($t) + interval($t), since some
+small extra amount of time is added to make sure that the timer does not
+expire before interval() elapses.  If this were not so, then 
+
+Changing end_time() while a timer is running will set the expiration time.
+Changing it while it is expired has no affect, since reset()ing a timer always
+clears the end_time().
+
+=cut
+
+
+sub end_time {
+   my IPC::Run::Timer $self = shift;
+   if ( @_ ) {
+      $self->{END_TIME} = shift;
+      _debug $self->name, ' end_time set to ', $self->{END_TIME}
+        if $self->{DEBUG} > 2 || _debugging_details;
+   }
+   return $self->{END_TIME};
+}
+
+
+=item exception
+
+   $x = $t->exception;
+   $t->exception( $x );
+   $t->exception( undef );
+
+Sets/gets the exception to throw, if any.  'undef' means that no
+exception will be thrown.  Exception does not need to be a scalar: you 
+may ask that references be thrown.
+
+=cut
+
+
+sub exception {
+   my IPC::Run::Timer $self = shift;
+   if ( @_ ) {
+      $self->{EXCEPTION} = shift;
+      _debug $self->name, ' exception set to ', $self->{EXCEPTION}
+        if $self->{DEBUG} || _debugging_details;
+   }
+   return $self->{EXCEPTION};
+}
+
+
+=item interval
+
+   $i = interval $t;
+   $i = $t->interval;
+   $t->interval( $i );
+
+Sets the interval.  Sets the end time based on the start_time() and the
+interval (and a little fudge) if the timer is running.
+
+=cut
+
+sub interval {
+   my IPC::Run::Timer $self = shift;
+   if ( @_ ) {
+      $self->{INTERVAL} = _parse_time( shift );
+      _debug $self->name, ' interval set to ', $self->{INTERVAL}
+        if $self->{DEBUG} > 2 || _debugging_details;
+
+      $self->_calc_end_time if $self->state;
+   }
+   return $self->{INTERVAL};
+}
+
+
+=item expire
+
+   expire $t;
+   $t->expire;
+
+Sets the state to expired (undef).
+Will throw an exception if one
+is defined and the timer was not already expired.  You can expire a
+reset timer without starting it.
+
+=cut
+
+
+sub expire {
+   my IPC::Run::Timer $self = shift;
+   if ( defined $self->state ) {
+      _debug $self->name . ' expired'
+        if $self->{DEBUG} || _debugging;
+
+      $self->state( undef );
+      croak $self->exception if $self->exception;
+   }
+   return undef;
+}
+
+
+=item is_running
+
+=cut
+
+
+sub is_running {
+   my IPC::Run::Timer $self = shift;
+   return $self->state ? 1 : 0;
+}
+
+
+=item is_reset
+
+=cut
+   
+sub is_reset {
+   my IPC::Run::Timer $self = shift;
+   return defined $self->state && $self->state == 0;
+}
+
+
+=item is_expired
+
+=cut
+
+sub is_expired {
+   my IPC::Run::Timer $self = shift;
+   return ! defined $self->state;
+}
+
+=item name
+
+Sets/gets this timer's name.  The name is only used for debugging
+purposes so you can tell which freakin' timer is doing what.
+
+=cut
+
+sub name {
+   my IPC::Run::Timer $self = shift;
+   $self->{NAME} = shift if @_;
+   return defined $self->{NAME}
+      ? $self->{NAME}
+      : defined $self->{EXCEPTION}
+         ? 'timeout'
+        : 'timer';
+}
+
+
+=item reset
+
+   reset $t;
+   $t->reset;
+
+Resets the timer to the non-running, non-expired state and clears
+the end_time().
+
+=cut
+
+sub reset {
+   my IPC::Run::Timer $self = shift;
+   $self->state( 0 );
+   $self->end_time( undef );
+   _debug $self->name . ' reset'
+      if $self->{DEBUG} || _debugging;
+
+   return undef;
+}
+
+
+=item start
+
+   start $t;
+   $t->start;
+   start $t, $interval;
+   start $t, $interval, $now;
+
+Starts or restarts a timer.  This always sets the start_time.  It sets the
+end_time based on the interval if the timer is running or if no end time
+has been set.
+
+You may pass an optional interval or current time value.
+
+Not passing a defined interval causes the previous interval setting to be
+re-used unless the timer is reset and an end_time has been set
+(an exception is thrown if no interval has been set).  
+
+Not passing a defined current time value causes the current time to be used.
+
+Passing a current time value is useful if you happen to have a time value
+lying around or if you want to make sure that several timers are started
+with the same concept of start time.  You might even need to lie to an
+IPC::Run::Timer, occasionally.
+
+=cut
+
+sub start {
+   my IPC::Run::Timer $self = shift;
+
+   my ( $interval, $now ) = map { _parse_time( $_ ) } @_;
+   $now = _parse_time( $now );
+   $now = time unless defined $now;
+
+   $self->interval( $interval ) if defined $interval;
+
+   ## start()ing a running or expired timer clears the end_time, so that the
+   ## interval is used.  So does specifying an interval.
+   $self->end_time( undef ) if ! $self->is_reset || $interval;
+
+   croak "IPC::Run: no timer interval or end_time defined for " . $self->name
+      unless defined $self->interval || defined $self->end_time;
+
+   $self->state( 1 );
+   $self->start_time( $now );
+   ## The "+ 1" is in case the START_TIME was sampled at the end of a
+   ## tick (which are one second long in this module).
+   $self->_calc_end_time
+      unless defined $self->end_time;
+
+   _debug(
+      $self->name, " started at ", $self->start_time,
+      ", with interval ", $self->interval, ", end_time ", $self->end_time
+   ) if $self->{DEBUG} || _debugging;
+   return undef;
+}
+
+
+=item start_time
+
+Sets/gets the start time, in seconds since the epoch.  Setting this manually
+is a bad idea, it's better to call L</start>() at the correct time.
+
+=cut
+
+
+sub start_time {
+   my IPC::Run::Timer $self = shift;
+   if ( @_ ) {
+      $self->{START_TIME} = _parse_time( shift );
+      _debug $self->name, ' start_time set to ', $self->{START_TIME}
+        if $self->{DEBUG} > 2 || _debugging;
+   }
+
+   return $self->{START_TIME};
+}
+
+
+=item state
+
+   $s = state $t;
+   $t->state( $s );
+
+Get/Set the current state.  Only use this if you really need to transfer the
+state to/from some variable.
+Use L</expire>, L</start>, L</reset>, L</is_expired>, L</is_running>,
+L</is_reset>.
+
+Note:  Setting the state to 'undef' to expire a timer will not throw an
+exception.
+
+=back
+
+=cut
+
+sub state {
+   my IPC::Run::Timer $self = shift;
+   if ( @_ ) {
+      $self->{STATE} = shift;
+      _debug $self->name, ' state set to ', $self->{STATE}
+        if $self->{DEBUG} > 2 || _debugging;
+   }
+   return $self->{STATE};
+}
+
+
+1;
+
+=pod
+
+=head1 TODO
+
+use Time::HiRes; if it's present.
+
+Add detection and parsing of [[[HH:]MM:]SS formatted times and intervals.
+
+=head1 AUTHOR
+
+Barrie Slaymaker <barries@slaysys.com>
+
+=cut
diff --git a/tools/cmake/scripts/IPC/Run/Win32Helper.pm b/tools/cmake/scripts/IPC/Run/Win32Helper.pm
new file mode 100644 (file)
index 0000000..ddbdadb
--- /dev/null
@@ -0,0 +1,489 @@
+package IPC::Run::Win32Helper;
+
+=pod
+
+=head1 NAME
+
+IPC::Run::Win32Helper - helper routines for IPC::Run on Win32 platforms.
+
+=head1 SYNOPSIS
+
+    use IPC::Run::Win32Helper;   # Exports all by default
+
+=head1 DESCRIPTION
+
+IPC::Run needs to use sockets to redirect subprocess I/O so that the select() loop
+will work on Win32. This seems to only work on WinNT and Win2K at this time, not
+sure if it will ever work on Win95 or Win98. If you have experience in this area, please
+contact me at barries@slaysys.com, thanks!.
+
+=cut
+
+use strict;
+use Carp;
+use IO::Handle;
+use vars qw{ $VERSION @ISA @EXPORT };
+BEGIN {
+       $VERSION = '0.90';
+       @ISA = qw( Exporter );
+       @EXPORT = qw(
+               win32_spawn
+               win32_parse_cmd_line
+               _dont_inherit
+               _inherit
+       );
+}
+
+require POSIX;
+
+use Text::ParseWords;
+use Win32::Process;
+use IPC::Run::Debug;
+use Win32API::File qw(
+   FdGetOsFHandle
+   SetHandleInformation
+   HANDLE_FLAG_INHERIT
+   INVALID_HANDLE_VALUE
+);
+
+## Takes an fd or a GLOB ref, never never never a Win32 handle.
+sub _dont_inherit {
+   for ( @_ ) {
+      next unless defined $_;
+      my $fd = $_;
+      $fd = fileno $fd if ref $fd;
+      _debug "disabling inheritance of ", $fd if _debugging_details;
+      my $osfh = FdGetOsFHandle $fd;
+      croak $^E if ! defined $osfh || $osfh == INVALID_HANDLE_VALUE;
+
+      SetHandleInformation( $osfh, HANDLE_FLAG_INHERIT, 0 );
+   }
+}
+
+sub _inherit {       #### REMOVE
+   for ( @_ ) {       #### REMOVE
+      next unless defined $_;       #### REMOVE
+      my $fd = $_;       #### REMOVE
+      $fd = fileno $fd if ref $fd;       #### REMOVE
+      _debug "enabling inheritance of ", $fd if _debugging_details;       #### REMOVE
+      my $osfh = FdGetOsFHandle $fd;       #### REMOVE
+      croak $^E if ! defined $osfh || $osfh == INVALID_HANDLE_VALUE;       #### REMOVE
+       #### REMOVE
+      SetHandleInformation( $osfh, HANDLE_FLAG_INHERIT, 1 );       #### REMOVE
+   }       #### REMOVE
+}       #### REMOVE
+       #### REMOVE
+#sub _inherit {
+#   for ( @_ ) {
+#      next unless defined $_;
+#      my $osfh = GetOsFHandle $_;
+#      croak $^E if ! defined $osfh || $osfh == INVALID_HANDLE_VALUE;
+#      SetHandleInformation( $osfh, HANDLE_FLAG_INHERIT, HANDLE_FLAG_INHERIT );
+#   }
+#}
+
+=pod
+
+=head1 FUNCTIONS
+
+=over
+
+=item optimize()
+
+Most common incantations of C<run()> (I<not> C<harness()>, C<start()>,
+or C<finish()>) now use temporary files to redirect input and output
+instead of pumper processes.
+
+Temporary files are used when sending to child processes if input is
+taken from a scalar with no filter subroutines.  This is the only time
+we can assume that the parent is not interacting with the child's
+redirected input as it runs.
+
+Temporary files are used when receiving from children when output is
+to a scalar or subroutine with or without filters, but only if
+the child in question closes its inputs or takes input from 
+unfiltered SCALARs or named files.  Normally, a child inherits its STDIN
+from its parent; to close it, use "0<&-" or the C<< noinherit => 1 >> option.
+If data is sent to the child from CODE refs, filehandles or from
+scalars through filters than the child's outputs will not be optimized
+because C<optimize()> assumes the parent is interacting with the child.
+It is ok if the output is filtered or handled by a subroutine, however.
+
+This assumes that all named files are real files (as opposed to named
+pipes) and won't change; and that a process is not communicating with
+the child indirectly (through means not visible to IPC::Run).
+These can be an invalid assumptions, but are the 99% case.
+Write me if you need an option to enable or disable optimizations; I
+suspect it will work like the C<binary()> modifier.
+
+To detect cases that you might want to optimize by closing inputs, try
+setting the C<IPCRUNDEBUG> environment variable to the special C<notopt>
+value:
+
+   C:> set IPCRUNDEBUG=notopt
+   C:> my_app_that_uses_IPC_Run.pl
+
+=item optimizer() rationalizations
+
+Only for that limited case can we be sure that it's ok to batch all the
+input in to a temporary file.  If STDIN is from a SCALAR or from a named
+file or filehandle (again, only in C<run()>), then outputs to CODE refs
+are also assumed to be safe enough to batch through a temp file,
+otherwise only outputs to SCALAR refs are batched.  This can cause a bit
+of grief if the parent process benefits from or relies on a bit of
+"early returns" coming in before the child program exits.  As long as
+the output is redirected to a SCALAR ref, this will not be visible.
+When output is redirected to a subroutine or (deprecated) filters, the
+subroutine will not get any data until after the child process exits,
+and it is likely to get bigger chunks of data at once.
+
+The reason for the optimization is that, without it, "pumper" processes
+are used to overcome the inconsistencies of the Win32 API.  We need to
+use anonymous pipes to connect to the child processes' stdin, stdout,
+and stderr, yet select() does not work on these.  select() only works on
+sockets on Win32.  So for each redirected child handle, there is
+normally a "pumper" process that connects to the parent using a
+socket--so the parent can select() on that fd--and to the child on an
+anonymous pipe--so the child can read/write a pipe.
+
+Using a socket to connect directly to the child (as at least one MSDN
+article suggests) seems to cause the trailing output from most children
+to be lost.  I think this is because child processes rarely close their
+stdout and stderr explicitly, and the winsock dll does not seem to flush
+output when a process that uses it exits without explicitly closing
+them.
+
+Because of these pumpers and the inherent slowness of Win32
+CreateProcess(), child processes with redirects are quite slow to
+launch; so this routine looks for the very common case of
+reading/writing to/from scalar references in a run() routine and
+converts such reads and writes in to temporary file reads and writes.
+
+Such files are marked as FILE_ATTRIBUTE_TEMPORARY to increase speed and
+as FILE_FLAG_DELETE_ON_CLOSE so it will be cleaned up when the child
+process exits (for input files).  The user's default permissions are
+used for both the temporary files and the directory that contains them,
+hope your Win32 permissions are secure enough for you.  Files are
+created with the Win32API::File defaults of
+FILE_SHARE_READ|FILE_SHARE_WRITE.
+
+Setting the debug level to "details" or "gory" will give detailed
+information about the optimization process; setting it to "basic" or
+higher will tell whether or not a given call is optimized.  Setting
+it to "notopt" will highlight those calls that aren't optimized.
+
+=cut
+
+sub optimize {
+   my ( $h ) = @_;
+
+   my @kids = @{$h->{KIDS}};
+
+   my $saw_pipe;
+
+   my ( $ok_to_optimize_outputs, $veto_output_optimization );
+
+   for my $kid ( @kids ) {
+      ( $ok_to_optimize_outputs, $veto_output_optimization ) = ()
+         unless $saw_pipe;
+
+      _debug
+         "Win32 optimizer: (kid $kid->{NUM}) STDIN piped, carrying over ok of non-SCALAR output optimization"
+         if _debugging_details && $ok_to_optimize_outputs;
+      _debug
+         "Win32 optimizer: (kid $kid->{NUM}) STDIN piped, carrying over veto of non-SCALAR output optimization"
+         if _debugging_details && $veto_output_optimization;
+
+      if ( $h->{noinherit} && ! $ok_to_optimize_outputs ) {
+        _debug
+           "Win32 optimizer: (kid $kid->{NUM}) STDIN not inherited from parent oking non-SCALAR output optimization"
+           if _debugging_details && $ok_to_optimize_outputs;
+        $ok_to_optimize_outputs = 1;
+      }
+
+      for ( @{$kid->{OPS}} ) {
+         if ( substr( $_->{TYPE}, 0, 1 ) eq "<" ) {
+            if ( $_->{TYPE} eq "<" ) {
+              if ( @{$_->{FILTERS}} > 1 ) {
+                 ## Can't assume that the filters are idempotent.
+              }
+               elsif ( ref $_->{SOURCE} eq "SCALAR"
+                 || ref $_->{SOURCE} eq "GLOB"
+                 || UNIVERSAL::isa( $_, "IO::Handle" )
+              ) {
+                  if ( $_->{KFD} == 0 ) {
+                     _debug
+                        "Win32 optimizer: (kid $kid->{NUM}) 0$_->{TYPE}",
+                        ref $_->{SOURCE},
+                        ", ok to optimize outputs"
+                        if _debugging_details;
+                     $ok_to_optimize_outputs = 1;
+                  }
+                  $_->{SEND_THROUGH_TEMP_FILE} = 1;
+                  next;
+               }
+               elsif ( ! ref $_->{SOURCE} && defined $_->{SOURCE} ) {
+                  if ( $_->{KFD} == 0 ) {
+                     _debug
+                        "Win32 optimizer: (kid $kid->{NUM}) 0<$_->{SOURCE}, ok to optimize outputs",
+                        if _debugging_details;
+                     $ok_to_optimize_outputs = 1;
+                  }
+                  next;
+               }
+            }
+            _debug
+               "Win32 optimizer: (kid $kid->{NUM}) ",
+               $_->{KFD},
+               $_->{TYPE},
+               defined $_->{SOURCE}
+                  ? ref $_->{SOURCE}      ? ref $_->{SOURCE}
+                                          : $_->{SOURCE}
+                  : defined $_->{FILENAME}
+                                          ? $_->{FILENAME}
+                                          : "",
+              @{$_->{FILTERS}} > 1 ? " with filters" : (),
+               ", VETOING output opt."
+               if _debugging_details || _debugging_not_optimized;
+            $veto_output_optimization = 1;
+         }
+         elsif ( $_->{TYPE} eq "close" && $_->{KFD} == 0 ) {
+            $ok_to_optimize_outputs = 1;
+            _debug "Win32 optimizer: (kid $kid->{NUM}) saw 0<&-, ok to optimize outputs"
+               if _debugging_details;
+         }
+         elsif ( $_->{TYPE} eq "dup" && $_->{KFD2} == 0 ) {
+            $veto_output_optimization = 1;
+            _debug "Win32 optimizer: (kid $kid->{NUM}) saw 0<&$_->{KFD2}, VETOING output opt."
+               if _debugging_details || _debugging_not_optimized;
+         }
+         elsif ( $_->{TYPE} eq "|" ) {
+            $saw_pipe = 1;
+         }
+      }
+
+      if ( ! $ok_to_optimize_outputs && ! $veto_output_optimization ) {
+         _debug
+            "Win32 optimizer: (kid $kid->{NUM}) child STDIN not redirected, VETOING non-SCALAR output opt."
+            if _debugging_details || _debugging_not_optimized;
+         $veto_output_optimization = 1;
+      }
+
+      if ( $ok_to_optimize_outputs && $veto_output_optimization ) {
+         $ok_to_optimize_outputs = 0;
+         _debug "Win32 optimizer: (kid $kid->{NUM}) non-SCALAR output optimizations VETOed"
+            if _debugging_details || _debugging_not_optimized;
+      }
+
+      ## SOURCE/DEST ARRAY means it's a filter.
+      ## TODO: think about checking to see if the final input/output of
+      ## a filter chain (an ARRAY SOURCE or DEST) is a scalar...but
+      ## we may be deprecating filters.
+
+      for ( @{$kid->{OPS}} ) {
+         if ( $_->{TYPE} eq ">" ) {
+            if ( ref $_->{DEST} eq "SCALAR"
+               || (
+                  ( @{$_->{FILTERS}} > 1
+                    || ref $_->{DEST} eq "CODE"
+                    || ref $_->{DEST} eq "ARRAY"  ## Filters?
+                 )
+                  && ( $ok_to_optimize_outputs && ! $veto_output_optimization ) 
+               )
+            ) {
+              $_->{RECV_THROUGH_TEMP_FILE} = 1;
+              next;
+            }
+           _debug
+              "Win32 optimizer: NOT optimizing (kid $kid->{NUM}) ",
+              $_->{KFD},
+              $_->{TYPE},
+              defined $_->{DEST}
+                 ? ref $_->{DEST}      ? ref $_->{DEST}
+                                         : $_->{SOURCE}
+                 : defined $_->{FILENAME}
+                                         ? $_->{FILENAME}
+                                         : "",
+                 @{$_->{FILTERS}} ? " with filters" : (),
+              if _debugging_details;
+         }
+      }
+   }
+
+}
+
+=pod
+
+=item win32_parse_cmd_line
+
+   @words = win32_parse_cmd_line( q{foo bar 'baz baz' "bat bat"} );
+
+returns 4 words. This parses like the bourne shell (see
+the bit about shellwords() in L<Text::ParseWords>), assuming we're
+trying to be a little cross-platform here.  The only difference is
+that "\" is *not* treated as an escape except when it precedes 
+punctuation, since it's used all over the place in DOS path specs.
+
+TODO: globbing? probably not (it's unDOSish).
+
+TODO: shebang emulation? Probably, but perhaps that should be part
+of Run.pm so all spawned processes get the benefit.
+
+LIMITATIONS: shellwords dies silently on malformed input like 
+
+   a\"
+
+=cut
+
+sub win32_parse_cmd_line {
+   my $line = shift;
+   $line =~ s{(\\[\w\s])}{\\$1}g;
+   return shellwords $line;
+}
+
+=pod
+
+=item win32_spawn
+
+Spawns a child process, possibly with STDIN, STDOUT, and STDERR (file descriptors 0, 1, and 2, respectively) redirected.
+
+B<LIMITATIONS>.
+
+Cannot redirect higher file descriptors due to lack of support for this in the
+Win32 environment.
+
+This can be worked around by marking a handle as inheritable in the
+parent (or leaving it marked; this is the default in perl), obtaining it's
+Win32 handle with C<Win32API::GetOSFHandle(FH)> or
+C<Win32API::FdGetOsFHandle($fd)> and passing it to the child using the command
+line, the environment, or any other IPC mechanism (it's a plain old integer).
+The child can then use C<OsFHandleOpen()> or C<OsFHandleOpenFd()> and possibly
+C<<open FOO ">&BAR">> or C<<open FOO ">&$fd>> as need be.  Ach, the pain!
+
+Remember to check the Win32 handle against INVALID_HANDLE_VALUE.
+
+=cut
+
+sub _save {
+   my ( $saved, $saved_as, $fd ) = @_;
+
+   ## We can only save aside the original fds once.
+   return if exists $saved->{$fd};
+
+   my $saved_fd = IPC::Run::_dup( $fd );
+   _dont_inherit $saved_fd;
+
+   $saved->{$fd} = $saved_fd;
+   $saved_as->{$saved_fd} = $fd;
+
+   _dont_inherit $saved->{$fd};
+}
+
+sub _dup2_gently {
+   my ( $saved, $saved_as, $fd1, $fd2 ) = @_;
+   _save $saved, $saved_as, $fd2;
+
+   if ( exists $saved_as->{$fd2} ) {
+      ## The target fd is colliding with a saved-as fd, gotta bump
+      ## the saved-as fd to another fd.
+      my $orig_fd = delete $saved_as->{$fd2};
+      my $saved_fd = IPC::Run::_dup( $fd2 );
+      _dont_inherit $saved_fd;
+
+      $saved->{$orig_fd} = $saved_fd;
+      $saved_as->{$saved_fd} = $orig_fd;
+   }
+   _debug "moving $fd1 to kid's $fd2" if _debugging_details;
+   IPC::Run::_dup2_rudely( $fd1, $fd2 );
+}
+
+sub win32_spawn {
+   my ( $cmd, $ops) = @_;
+
+   ## NOTE: The debug pipe write handle is passed to pump processes as STDOUT.
+   ## and is not to the "real" child process, since they would not know
+   ## what to do with it...unlike Unix, we have no code executing in the
+   ## child before the "real" child is exec()ed.
+   
+   my %saved;      ## Map of parent's orig fd -> saved fd
+   my %saved_as;   ## Map of parent's saved fd -> orig fd, used to
+                    ## detect collisions between a KFD and the fd a
+                   ## parent's fd happened to be saved to.
+   
+   for my $op ( @$ops ) {
+      _dont_inherit $op->{FD}  if defined $op->{FD};
+
+      if ( defined $op->{KFD} && $op->{KFD} > 2 ) {
+        ## TODO: Detect this in harness()
+        ## TODO: enable temporary redirections if ever necessary, not
+        ## sure why they would be...
+        ## 4>&1 1>/dev/null 1>&4 4>&-
+         croak "Can't redirect fd #", $op->{KFD}, " on Win32";
+      }
+
+      ## This is very similar logic to IPC::Run::_do_kid_and_exit().
+      if ( defined $op->{TFD} ) {
+        unless ( $op->{TFD} == $op->{KFD} ) {
+           _dup2_gently \%saved, \%saved_as, $op->{TFD}, $op->{KFD};
+           _dont_inherit $op->{TFD};
+        }
+      }
+      elsif ( $op->{TYPE} eq "dup" ) {
+         _dup2_gently \%saved, \%saved_as, $op->{KFD1}, $op->{KFD2}
+            unless $op->{KFD1} == $op->{KFD2};
+      }
+      elsif ( $op->{TYPE} eq "close" ) {
+        _save \%saved, \%saved_as, $op->{KFD};
+        IPC::Run::_close( $op->{KFD} );
+      }
+      elsif ( $op->{TYPE} eq "init" ) {
+        ## TODO: detect this in harness()
+         croak "init subs not allowed on Win32";
+      }
+   }
+
+   my $process;
+   my $cmd_line = join " ", map {
+      ( my $s = $_ ) =~ s/"/"""/g;
+      $s = qq{"$s"} if /[\"\s]|^$/;
+      $s;
+   } @$cmd;
+
+   _debug "cmd line: ", $cmd_line
+      if _debugging;
+
+   Win32::Process::Create( 
+      $process,
+      $cmd->[0],
+      $cmd_line,
+      1,  ## Inherit handles
+      NORMAL_PRIORITY_CLASS,
+      ".",
+   ) or croak "$!: Win32::Process::Create()";
+
+   for my $orig_fd ( keys %saved ) {
+      IPC::Run::_dup2_rudely( $saved{$orig_fd}, $orig_fd );
+      IPC::Run::_close( $saved{$orig_fd} );
+   }
+
+   return ( $process->GetProcessID(), $process );
+}
+
+
+1;
+
+=pod
+
+=back
+
+=head1 AUTHOR
+
+Barries Slaymaker <barries@slaysys.com>.  Funded by Perforce Software, Inc.
+
+=head1 COPYRIGHT
+
+Copyright 2001, Barrie Slaymaker, All Rights Reserved.
+
+You may use this under the terms of either the GPL 2.0 or the Artistic License.
+
+=cut
diff --git a/tools/cmake/scripts/IPC/Run/Win32IO.pm b/tools/cmake/scripts/IPC/Run/Win32IO.pm
new file mode 100644 (file)
index 0000000..69afd8e
--- /dev/null
@@ -0,0 +1,573 @@
+package IPC::Run::Win32IO;
+
+=pod
+
+=head1 NAME
+
+IPC::Run::Win32IO - helper routines for IPC::Run on Win32 platforms.
+
+=head1 SYNOPSIS
+
+    use IPC::Run::Win32IO;   # Exports all by default
+
+=head1 DESCRIPTION
+
+IPC::Run needs to use sockets to redirect subprocess I/O so that the select()
+loop will work on Win32. This seems to only work on WinNT and Win2K at this
+time, not sure if it will ever work on Win95 or Win98. If you have experience
+in this area, please contact me at barries@slaysys.com, thanks!.
+
+=head1 DESCRIPTION
+
+A specialized IO class used on Win32.
+
+=cut
+
+use strict;
+use Carp;
+use IO::Handle;
+use Socket;
+require POSIX;
+
+use vars qw{$VERSION};
+BEGIN {
+       $VERSION = '0.90';
+}
+
+use Socket qw( IPPROTO_TCP TCP_NODELAY );
+use Symbol;
+use Text::ParseWords;
+use Win32::Process;
+use IPC::Run::Debug qw( :default _debugging_level );
+use IPC::Run::Win32Helper qw( _inherit _dont_inherit );
+use Fcntl qw( O_TEXT O_RDONLY );
+
+use base qw( IPC::Run::IO );
+my @cleanup_fields;
+BEGIN {
+   ## These fields will be set to undef in _cleanup to close
+   ## the handles.
+   @cleanup_fields = (
+      'SEND_THROUGH_TEMP_FILE', ## Set by WinHelper::optimize()
+      'RECV_THROUGH_TEMP_FILE', ## Set by WinHelper::optimize()
+      'TEMP_FILE_NAME',         ## The name of the temp file, needed for
+                                ## error reporting / debugging only.
+
+      'PARENT_HANDLE',       ## The handle of the socket for the parent
+      'PUMP_SOCKET_HANDLE',  ## The socket handle for the pump
+      'PUMP_PIPE_HANDLE',    ## The anon pipe handle for the pump
+      'CHILD_HANDLE',        ## The anon pipe handle for the child
+
+      'TEMP_FILE_HANDLE',    ## The Win32 filehandle for the temp file
+   );
+}
+
+## REMOVE OSFHandleOpen
+use Win32API::File qw(
+   GetOsFHandle
+   OsFHandleOpenFd
+   OsFHandleOpen
+   FdGetOsFHandle
+   SetHandleInformation
+   SetFilePointer
+   HANDLE_FLAG_INHERIT
+   INVALID_HANDLE_VALUE
+
+   createFile
+   WriteFile
+   ReadFile
+   CloseHandle
+
+   FILE_ATTRIBUTE_TEMPORARY
+   FILE_FLAG_DELETE_ON_CLOSE
+   FILE_FLAG_WRITE_THROUGH
+
+   FILE_BEGIN
+);
+
+#   FILE_ATTRIBUTE_HIDDEN
+#   FILE_ATTRIBUTE_SYSTEM
+
+
+BEGIN {
+   ## Force AUTOLOADED constants to be, well, constant by getting them
+   ## to AUTOLOAD before compilation continues.  Sigh.
+   () = (
+      SOL_SOCKET,
+      SO_REUSEADDR,
+      IPPROTO_TCP,
+      TCP_NODELAY,
+      HANDLE_FLAG_INHERIT,
+      INVALID_HANDLE_VALUE,
+   );
+}
+
+use constant temp_file_flags => (
+   FILE_ATTRIBUTE_TEMPORARY()   |
+   FILE_FLAG_DELETE_ON_CLOSE()  |
+   FILE_FLAG_WRITE_THROUGH()
+);
+
+#   FILE_ATTRIBUTE_HIDDEN()    |
+#   FILE_ATTRIBUTE_SYSTEM()    |
+my $tmp_file_counter;
+my $tmp_dir;
+
+sub _cleanup {
+    my IPC::Run::Win32IO $self = shift;
+    my ( $harness ) = @_;
+
+    $self->_recv_through_temp_file( $harness )
+       if $self->{RECV_THROUGH_TEMP_FILE};
+
+    CloseHandle( $self->{TEMP_FILE_HANDLE} )
+       if defined $self->{TEMP_FILE_HANDLE};
+
+    $self->{$_} = undef for @cleanup_fields;
+}
+
+
+sub _create_temp_file {
+   my IPC::Run::Win32IO $self = shift;
+
+   ## Create a hidden temp file that Win32 will delete when we close
+   ## it.
+   unless ( defined $tmp_dir ) {
+      $tmp_dir = File::Spec->catdir(
+         File::Spec->tmpdir, "IPC-Run.tmp"
+      );
+
+      ## Trust in the user's umask.
+      ## This could possibly be a security hole, perhaps
+      ## we should offer an option.  Hmmmm, really, people coding
+      ## security conscious apps should audit this code and
+      ## tell me how to make it better.  Nice cop-out :).
+      unless ( -d $tmp_dir ) {
+         mkdir $tmp_dir or croak "$!: $tmp_dir";
+      }
+   }
+
+   $self->{TEMP_FILE_NAME} = File::Spec->catfile(
+      ## File name is designed for easy sorting and not conflicting
+      ## with other processes.  This should allow us to use "t"runcate
+      ## access in CreateFile in case something left some droppings
+      ## around (which should never happen because we specify
+      ## FLAG_DELETE_ON_CLOSE.
+      ## heh, belt and suspenders are better than bug reports; God forbid
+      ## that NT should ever crash before a temp file gets deleted!
+      $tmp_dir, sprintf "Win32io-%06d-%08d", $$, $tmp_file_counter++
+   );
+
+   $self->{TEMP_FILE_HANDLE} = createFile(
+      $self->{TEMP_FILE_NAME},
+      "trw",         ## new, truncate, read, write
+      {
+         Flags      => temp_file_flags,
+      },
+   ) or croak "Can't create temporary file, $self->{TEMP_FILE_NAME}: $^E";
+
+   $self->{TFD} = OsFHandleOpenFd $self->{TEMP_FILE_HANDLE}, 0;
+   $self->{FD} = undef;
+
+   _debug
+      "Win32 Optimizer: temp file (",
+      $self->{KFD},
+      $self->{TYPE},
+      $self->{TFD},
+      ", fh ",
+      $self->{TEMP_FILE_HANDLE},
+      "): ",
+      $self->{TEMP_FILE_NAME}
+      if _debugging_details;
+}
+
+
+sub _reset_temp_file_pointer {
+   my $self = shift;
+   SetFilePointer( $self->{TEMP_FILE_HANDLE}, 0, 0, FILE_BEGIN )
+      or confess "$^E seeking on (fd $self->{TFD}) $self->{TEMP_FILE_NAME} for kid's fd $self->{KFD}";
+}
+
+
+sub _send_through_temp_file {
+   my IPC::Run::Win32IO $self = shift;
+
+   _debug
+      "Win32 optimizer: optimizing "
+      . " $self->{KFD} $self->{TYPE} temp file instead of ",
+         ref $self->{SOURCE} || $self->{SOURCE}
+      if _debugging_details;
+
+   $self->_create_temp_file;
+
+   if ( defined ${$self->{SOURCE}} ) {
+      my $bytes_written = 0;
+      my $data_ref;
+      if ( $self->binmode ) {
+        $data_ref = $self->{SOURCE};
+      }
+      else {
+         my $data = ${$self->{SOURCE}};  # Ugh, a copy.
+        $data =~ s/(?<!\r)\n/\r\n/g;
+        $data_ref = \$data;
+      }
+
+      WriteFile(
+         $self->{TEMP_FILE_HANDLE},
+         $$data_ref,
+         0,              ## Write entire buffer
+         $bytes_written,
+         [],             ## Not overlapped.
+      ) or croak
+         "$^E writing $self->{TEMP_FILE_NAME} for kid to read on fd $self->{KFD}";
+      _debug
+         "Win32 optimizer: wrote $bytes_written to temp file $self->{TEMP_FILE_NAME}"
+         if _debugging_data;
+
+      $self->_reset_temp_file_pointer;
+
+   }
+
+
+   _debug "Win32 optimizer: kid to read $self->{KFD} from temp file on $self->{TFD}"
+      if _debugging_details;
+}
+
+
+sub _init_recv_through_temp_file {
+   my IPC::Run::Win32IO $self = shift;
+
+   $self->_create_temp_file;
+}
+
+
+## TODO: Use the Win32 API in the select loop to see if the file has grown
+## and read it incrementally if it has.
+sub _recv_through_temp_file {
+   my IPC::Run::Win32IO $self = shift;
+
+   ## This next line kicks in if the run() never got to initting things
+   ## and needs to clean up.
+   return undef unless defined $self->{TEMP_FILE_HANDLE};
+
+   push @{$self->{FILTERS}}, sub {
+      my ( undef, $out_ref ) = @_;
+
+      return undef unless defined $self->{TEMP_FILE_HANDLE};
+
+      my $r;
+      my $s;
+      ReadFile(
+        $self->{TEMP_FILE_HANDLE},
+        $s,
+        999_999,  ## Hmmm, should read the size.
+        $r,
+        []
+      ) or croak "$^E reading from $self->{TEMP_FILE_NAME}";
+
+      _debug "ReadFile( $self->{TFD} ) = $r chars '$s'" if _debugging_data;
+
+      return undef unless $r;
+
+      $s =~ s/\r\n/\n/g unless $self->binmode;
+
+      my $pos = pos $$out_ref;
+      $$out_ref .= $s;
+      pos( $out_ref ) = $pos;
+      return 1;
+   };
+
+   my ( $harness ) = @_;
+
+   $self->_reset_temp_file_pointer;
+
+   1 while $self->_do_filters( $harness );
+
+   pop @{$self->{FILTERS}};
+
+   IPC::Run::_close( $self->{TFD} );
+}
+
+=head1 SUBROUTINES
+
+=over
+
+=item poll
+
+Windows version of IPC::Run::IP::poll.
+
+=back
+
+=cut
+
+sub poll {
+   my IPC::Run::Win32IO $self = shift;
+
+   return if $self->{SEND_THROUGH_TEMP_FILE} || $self->{RECV_THROUGH_TEMP_FILE};
+
+   return $self->SUPER::poll( @_ );
+}
+
+
+## When threaded Perls get good enough, we should use threads here.
+## The problem with threaded perls is that they dup() all sorts of
+## filehandles and fds and don't allow sufficient control over
+## closing off the ones we don't want.
+
+sub _spawn_pumper {
+   my ( $stdin, $stdout, $debug_fd, $binmode, $child_label, @opts ) = @_;
+   my ( $stdin_fd, $stdout_fd ) = ( fileno $stdin, fileno $stdout );
+
+   _debug "pumper stdin = ", $stdin_fd if _debugging_details;
+   _debug "pumper stdout = ", $stdout_fd if _debugging_details;
+   _inherit $stdin_fd, $stdout_fd, $debug_fd;
+   my @I_options = map qq{"-I$_"}, @INC;
+
+   my $cmd_line = join( " ",
+      qq{"$^X"},
+      @I_options,
+      qw(-MIPC::Run::Win32Pump -e 1 ),
+## I'm using this clunky way of passing filehandles to the child process
+## in order to avoid some kind of premature closure of filehandles
+## problem I was having with VCP's test suite when passing them
+## via CreateProcess.  All of the ## REMOVE code is stuff I'd like
+## to be rid of and the ## ADD code is what I'd like to use.
+      FdGetOsFHandle( $stdin_fd ), ## REMOVE
+      FdGetOsFHandle( $stdout_fd ), ## REMOVE
+      FdGetOsFHandle( $debug_fd ), ## REMOVE
+      $binmode ? 1 : 0,
+      $$, $^T, _debugging_level, qq{"$child_label"},
+      @opts
+   );
+
+#   open SAVEIN,  "<&STDIN"  or croak "$! saving STDIN";       #### ADD
+#   open SAVEOUT, ">&STDOUT" or croak "$! saving STDOUT";       #### ADD
+#   open SAVEERR, ">&STDERR" or croak "$! saving STDERR";       #### ADD
+#   _dont_inherit \*SAVEIN;       #### ADD
+#   _dont_inherit \*SAVEOUT;       #### ADD
+#   _dont_inherit \*SAVEERR;       #### ADD
+#   open STDIN,  "<&$stdin_fd"  or croak "$! dup2()ing $stdin_fd (pumper's STDIN)";       #### ADD
+#   open STDOUT, ">&$stdout_fd" or croak "$! dup2()ing $stdout_fd (pumper's STDOUT)";       #### ADD
+#   open STDERR, ">&$debug_fd" or croak "$! dup2()ing $debug_fd (pumper's STDERR/debug_fd)";       #### ADD
+
+   _debug "pump cmd line: ", $cmd_line if _debugging_details;
+
+   my $process;
+   Win32::Process::Create( 
+      $process,
+      $^X,
+      $cmd_line,
+      1,  ## Inherit handles
+      NORMAL_PRIORITY_CLASS,
+      ".",
+   ) or croak "$!: Win32::Process::Create()";
+
+#   open STDIN,  "<&SAVEIN"  or croak "$! restoring STDIN";       #### ADD
+#   open STDOUT, ">&SAVEOUT" or croak "$! restoring STDOUT";       #### ADD
+#   open STDERR, ">&SAVEERR" or croak "$! restoring STDERR";       #### ADD
+#   close SAVEIN             or croak "$! closing SAVEIN";       #### ADD
+#   close SAVEOUT            or croak "$! closing SAVEOUT";       #### ADD
+#   close SAVEERR            or croak "$! closing SAVEERR";       #### ADD
+
+   close $stdin  or croak "$! closing pumper's stdin in parent";
+   close $stdout or croak "$! closing pumper's stdout in parent";
+   # Don't close $debug_fd, we need it, as do other pumpers.
+
+   # Pause a moment to allow the child to get up and running and emit
+   # debug messages.  This does not always work.
+   #   select undef, undef, undef, 1 if _debugging_details;
+
+   _debug "_spawn_pumper pid = ", $process->GetProcessID 
+      if _debugging_data;
+}
+
+
+my $next_port = 2048;
+my $loopback  = inet_aton "127.0.0.1";
+my $tcp_proto = getprotobyname('tcp');
+croak "$!: getprotobyname('tcp')" unless defined $tcp_proto;
+
+sub _socket {
+   my ( $server ) = @_;
+   $server ||= gensym;
+   my $client = gensym;
+
+   my $listener = gensym;
+   socket $listener, PF_INET, SOCK_STREAM, $tcp_proto
+      or croak "$!: socket()";
+   setsockopt $listener, SOL_SOCKET, SO_REUSEADDR, pack("l", 0)
+      or croak "$!: setsockopt()";
+
+   my $port;
+   my @errors;
+PORT_FINDER_LOOP:
+   {
+      $port = $next_port;
+      $next_port = 2048 if ++$next_port > 65_535; 
+      unless ( bind $listener, sockaddr_in( $port, $loopback ) ) {
+        push @errors, "$! on port $port";
+        croak join "\n", @errors if @errors > 10;
+         goto PORT_FINDER_LOOP;
+      }
+   }
+
+   _debug "win32 port = $port" if _debugging_details;
+
+   listen $listener, my $queue_size = 1
+      or croak "$!: listen()";
+
+   {
+      socket $client, PF_INET, SOCK_STREAM, $tcp_proto
+         or croak "$!: socket()";
+
+      my $paddr = sockaddr_in($port, $loopback );
+
+      connect $client, $paddr
+         or croak "$!: connect()";
+    
+      croak "$!: accept" unless defined $paddr;
+
+      ## The windows "default" is SO_DONTLINGER, which should make
+      ## sure all socket data goes through.  I have my doubts based
+      ## on experimentation, but nothing prompts me to set SO_LINGER
+      ## at this time...
+      setsockopt $client, IPPROTO_TCP, TCP_NODELAY, pack("l", 0)
+        or croak "$!: setsockopt()";
+   }
+
+   {
+      _debug "accept()ing on port $port" if _debugging_details;
+      my $paddr = accept( $server, $listener );
+      croak "$!: accept()" unless defined $paddr;
+   }
+
+   _debug
+      "win32 _socket = ( ", fileno $server, ", ", fileno $client, " ) on port $port" 
+      if _debugging_details;
+   return ( $server, $client );
+}
+
+
+sub _open_socket_pipe {
+   my IPC::Run::Win32IO $self = shift;
+   my ( $debug_fd, $parent_handle ) = @_;
+
+   my $is_send_to_child = $self->dir eq "<";
+
+   $self->{CHILD_HANDLE}     = gensym;
+   $self->{PUMP_PIPE_HANDLE} = gensym;
+
+   ( 
+      $self->{PARENT_HANDLE},
+      $self->{PUMP_SOCKET_HANDLE}
+   ) = _socket $parent_handle;
+
+   ## These binmodes seem to have no effect on Win2K, but just to be safe
+   ## I do them.
+   binmode $self->{PARENT_HANDLE}      or die $!;
+   binmode $self->{PUMP_SOCKET_HANDLE} or die $!;
+
+_debug "PUMP_SOCKET_HANDLE = ", fileno $self->{PUMP_SOCKET_HANDLE}
+   if _debugging_details;
+##my $buf;
+##$buf = "write on child end of " . fileno( $self->{WRITE_HANDLE} ) . "\n\n\n\n\n";
+##POSIX::write(fileno $self->{WRITE_HANDLE}, $buf, length $buf) or warn "$! in syswrite";
+##$buf = "write on parent end of " . fileno( $self->{CHILD_HANDLE} ) . "\r\n";
+##POSIX::write(fileno $self->{CHILD_HANDLE},$buf, length $buf) or warn "$! in syswrite";
+##   $self->{CHILD_HANDLE}->autoflush( 1 );
+##   $self->{WRITE_HANDLE}->autoflush( 1 );
+
+   ## Now fork off a data pump and arrange to return the correct fds.
+   if ( $is_send_to_child ) {
+      pipe $self->{CHILD_HANDLE}, $self->{PUMP_PIPE_HANDLE}
+         or croak "$! opening child pipe";
+_debug "CHILD_HANDLE = ", fileno $self->{CHILD_HANDLE}
+   if _debugging_details;
+_debug "PUMP_PIPE_HANDLE = ", fileno $self->{PUMP_PIPE_HANDLE}
+   if _debugging_details;
+   }
+   else {
+      pipe $self->{PUMP_PIPE_HANDLE}, $self->{CHILD_HANDLE}
+         or croak "$! opening child pipe";
+_debug "CHILD_HANDLE = ", fileno $self->{CHILD_HANDLE}
+   if _debugging_details;
+_debug "PUMP_PIPE_HANDLE = ", fileno $self->{PUMP_PIPE_HANDLE}
+   if _debugging_details;
+   }
+
+   ## These binmodes seem to have no effect on Win2K, but just to be safe
+   ## I do them.
+   binmode $self->{CHILD_HANDLE};
+   binmode $self->{PUMP_PIPE_HANDLE};
+
+   ## No child should ever see this.
+   _dont_inherit $self->{PARENT_HANDLE};
+
+   ## We clear the inherit flag so these file descriptors are not inherited.
+   ## It'll be dup()ed on to STDIN/STDOUT/STDERR before CreateProcess is
+   ## called and *that* fd will be inheritable.
+   _dont_inherit $self->{PUMP_SOCKET_HANDLE};
+   _dont_inherit $self->{PUMP_PIPE_HANDLE};
+   _dont_inherit $self->{CHILD_HANDLE};
+
+   ## Need to return $self so the HANDLEs don't get freed.
+   ## Return $self, $parent_fd, $child_fd
+   my ( $parent_fd, $child_fd ) = (
+      fileno $self->{PARENT_HANDLE},
+      fileno $self->{CHILD_HANDLE}
+   );
+
+   ## Both PUMP_..._HANDLEs will be closed, no need to worry about
+   ## inheritance.
+   _debug "binmode on" if _debugging_data && $self->binmode;
+   _spawn_pumper(
+      $is_send_to_child
+        ? ( $self->{PUMP_SOCKET_HANDLE}, $self->{PUMP_PIPE_HANDLE} )
+        : ( $self->{PUMP_PIPE_HANDLE}, $self->{PUMP_SOCKET_HANDLE} ),
+      $debug_fd,
+      $self->binmode,
+      $child_fd . $self->dir . "pump" . $self->dir . $parent_fd,
+   );
+
+{
+my $foo;
+confess "PARENT_HANDLE no longer open"
+   unless POSIX::read( $parent_fd, $foo, 0 );
+}
+
+   _debug "win32_fake_pipe = ( $parent_fd, $child_fd )"
+      if _debugging_details;
+
+   $self->{FD}  = $parent_fd;
+   $self->{TFD} = $child_fd;
+}
+
+sub _do_open {
+   my IPC::Run::Win32IO $self = shift;
+
+   if ( $self->{SEND_THROUGH_TEMP_FILE} ) {
+      return $self->_send_through_temp_file( @_ );
+   }
+   elsif ( $self->{RECV_THROUGH_TEMP_FILE} ) {
+      return $self->_init_recv_through_temp_file( @_ );
+   }
+   else {
+      return $self->_open_socket_pipe( @_ );
+   }
+}
+
+1;
+
+=pod
+
+=head1 AUTHOR
+
+Barries Slaymaker <barries@slaysys.com>.  Funded by Perforce Software, Inc.
+
+=head1 COPYRIGHT
+
+Copyright 2001, Barrie Slaymaker, All Rights Reserved.
+
+You may use this under the terms of either the GPL 2.0 or the Artistic License.
+
+=cut
diff --git a/tools/cmake/scripts/IPC/Run/Win32Pump.pm b/tools/cmake/scripts/IPC/Run/Win32Pump.pm
new file mode 100644 (file)
index 0000000..ea7be05
--- /dev/null
@@ -0,0 +1,170 @@
+package IPC::Run::Win32Pump;
+
+=pod
+
+=head1 NAME
+
+IPC::Run::Win32Pump - helper processes to shovel data to/from parent, child
+
+=head1 SYNOPSIS
+
+Internal use only; see IPC::Run::Win32IO and best of luck to you.
+
+=head1 DESCRIPTION
+
+See L<IPC::Run::Win32Helper|IPC::Run::Win32Helper> for details.  This
+module is used in subprocesses that are spawned to shovel data to/from
+parent processes from/to their child processes.  Where possible, pumps
+are optimized away.
+
+NOTE: This is not a real module: it's a script in module form, designed
+to be run like
+
+   $^X -MIPC::Run::Win32Pumper -e 1 ...
+
+It parses a bunch of command line parameters from IPC::Run::Win32IO.
+
+=cut
+
+use strict;
+use vars qw{$VERSION};
+BEGIN {
+       $VERSION = '0.90';
+}
+
+use Win32API::File qw(
+   OsFHandleOpen
+);
+
+
+my ( $stdin_fh, $stdout_fh, $debug_fh, $binmode, $parent_pid, $parent_start_time, $debug, $child_label );
+BEGIN {
+   ( $stdin_fh, $stdout_fh, $debug_fh, $binmode, $parent_pid, $parent_start_time, $debug, $child_label ) = @ARGV;
+   ## Rather than letting IPC::Run::Debug export all-0 constants
+   ## when not debugging, we do it manually in order to not even
+   ## load IPC::Run::Debug.
+   if ( $debug ) {
+      eval "use IPC::Run::Debug qw( :default _debug_init ); 1;"
+        or die $@;
+   }
+   else {
+      eval <<STUBS_END or die $@;
+        sub _debug {}
+        sub _debug_init {}
+        sub _debugging() { 0 }
+        sub _debugging_data() { 0 }
+        sub _debugging_details() { 0 }
+        sub _debugging_gory_details() { 0 }
+        1;
+STUBS_END
+   }
+}
+
+## For some reason these get created with binmode on.  AAargh, gotta       #### REMOVE
+## do it by hand below.       #### REMOVE
+if ( $debug ) {       #### REMOVE
+close STDERR;       #### REMOVE
+OsFHandleOpen( \*STDERR, $debug_fh, "w" )       #### REMOVE
+ or print "$! opening STDERR as Win32 handle $debug_fh in pumper $$";       #### REMOVE
+}       #### REMOVE
+close STDIN;       #### REMOVE
+OsFHandleOpen( \*STDIN, $stdin_fh, "r" )       #### REMOVE
+or die "$! opening STDIN as Win32 handle $stdin_fh in pumper $$";       #### REMOVE
+close STDOUT;       #### REMOVE
+OsFHandleOpen( \*STDOUT, $stdout_fh, "w" )       #### REMOVE
+or die "$! opening STDOUT as Win32 handle $stdout_fh in pumper $$";       #### REMOVE
+
+binmode STDIN;
+binmode STDOUT;
+$| = 1;
+select STDERR; $| = 1; select STDOUT;
+
+$child_label ||= "pump";
+_debug_init(
+$parent_pid,
+$parent_start_time,
+$debug,
+fileno STDERR,
+$child_label,
+);
+
+_debug "Entered" if _debugging_details;
+
+# No need to close all fds; win32 doesn't seem to pass any on to us.
+$| = 1;
+my $buf;
+my $total_count = 0;
+while (1) {
+my $count = sysread STDIN, $buf, 10_000;
+last unless $count;
+if ( _debugging_gory_details ) {
+ my $msg = "'$buf'";
+ substr( $msg, 100, -1 ) = '...' if length $msg > 100;
+ $msg =~ s/\n/\\n/g;
+ $msg =~ s/\r/\\r/g;
+ $msg =~ s/\t/\\t/g;
+ $msg =~ s/([\000-\037\177-\277])/sprintf "\0x%02x", ord $1/eg;
+ _debug sprintf( "%5d chars revc: ", $count ), $msg;
+}
+$total_count += $count;
+$buf =~ s/\r//g unless $binmode;
+if ( _debugging_gory_details ) {
+ my $msg = "'$buf'";
+ substr( $msg, 100, -1 ) = '...' if length $msg > 100;
+ $msg =~ s/\n/\\n/g;
+ $msg =~ s/\r/\\r/g;
+ $msg =~ s/\t/\\t/g;
+ $msg =~ s/([\000-\037\177-\277])/sprintf "\0x%02x", ord $1/eg;
+ _debug sprintf( "%5d chars sent: ", $count ), $msg;
+}
+print $buf;
+}
+
+_debug "Exiting, transferred $total_count chars" if _debugging_details;
+
+## Perform a graceful socket shutdown.  Windows defaults to SO_DONTLINGER,
+## which should cause a "graceful shutdown in the background" on sockets.
+## but that's only true if the process closes the socket manually, it
+## seems; if the process exits and lets the OS clean up, the OS is not
+## so kind.  STDOUT is not always a socket, of course, but it won't hurt
+## to close a pipe and may even help.  With a closed source OS, who
+## can tell?
+##
+## In any case, this close() is one of the main reasons we have helper
+## processes; if the OS closed socket fds gracefully when an app exits,
+## we'd just redirect the client directly to what is now the pump end 
+## of the socket.  As it is, however, we need to let the client play with
+## pipes, which don't have the abort-on-app-exit behavior, and then
+## adapt to the sockets in the helper processes to allow the parent to
+## select.
+##
+## Possible alternatives / improvements:
+## 
+## 1) use helper threads instead of processes.  I don't trust perl's threads
+## as of 5.005 or 5.6 enough (which may be myopic of me).
+##
+## 2) figure out if/how to get at WaitForMultipleObjects() with pipe
+## handles.  May be able to take the Win32 handle and pass it to 
+## Win32::Event::wait_any, dunno.
+## 
+## 3) Use Inline::C or a hand-tooled XS module to do helper threads.
+## This would be faster than #1, but would require a ppm distro.
+##
+close STDOUT;
+close STDERR;
+
+1;
+
+=pod
+
+=head1 AUTHOR
+
+Barries Slaymaker <barries@slaysys.com>.  Funded by Perforce Software, Inc.
+
+=head1 COPYRIGHT
+
+Copyright 2001, Barrie Slaymaker, All Rights Reserved.
+
+You may use this under the terms of either the GPL 2.0 ir the Artistic License.
+
+=cut
similarity index 98%
rename from tools/cmake/Scripts/generate_memcheck_tests.pl
rename to tools/cmake/scripts/generate_memcheck_tests.pl
index fc4fd61..62ec9f6 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2012-2014. The SimGrid Team.
 # All rights reserved.
@@ -7,11 +7,12 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 
-# input file = AddTest.txt
+# input file = Test.txt
 
 if ( $#ARGV != 1 ) {
-    die "Usage: generate_memcheck_tests.pl <CMAKE_HOME_DIRECTORY> AddTests.cmake\n";
+    die "Usage: generate_memcheck_tests.pl <CMAKE_HOME_DIRECTORY> Tests.cmake\n";
 }
 
 my ($proj_dir) = $ARGV[0];
similarity index 95%
rename from tools/cmake/Scripts/my_valgrind.pl
rename to tools/cmake/scripts/my_valgrind.pl
index 073b4b8..3b273d5 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2012-2014. The SimGrid Team.
 # All rights reserved.
@@ -7,6 +7,8 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
+
 my @argv = ("valgrind");
 my $count = 0;
 
similarity index 91%
rename from tools/cmake/Scripts/update_tesh.pl
rename to tools/cmake/scripts/update_tesh.pl
index 7c340b4..bc78f15 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2012, 2014. The SimGrid Team.
 # All rights reserved.
@@ -7,9 +7,10 @@
 # under the terms of the license (GNU LGPL) which comes with this package.
 
 use strict;
+use warnings;
 
 if($#ARGV!=1) {
-    die "Usage: perl make_tesh.pl <directory> <old.tesh>\n";
+    die "Usage: perl update_tesh.pl <directory> <old.tesh>\n";
 }
 
 my($directory)=$ARGV[0];
index 44b9e7b..96a9cda 100644 (file)
@@ -27,9 +27,6 @@
        #endif
 #endif
 
-#cmakedefine SIZEOF_INT @SIZEOF_INT@
-#cmakedefine SIZEOF_VOIDP @SIZEOF_VOIDP@
-
 /* If __thread is available */
 #cmakedefine HAVE_THREAD_LOCAL_STORAGE @HAVE_THREAD_LOCAL_STORAGE@
 
 #cmakedefine __VISUALC__ @__VISUALC__@
 #cmakedefine __BORLANDC__ @__BORLANDC__@
 #cmakedefine APPLE @APPLE@
-#ifdef _XBT_WIN32
-       #ifndef __GNUC__
-               #cmakedefine __GNUC__ @__GNUC__@
-       #endif
+#ifdef _MSC_VER
+       #define HAVE_VA_COPY
 #endif
 /* Set to true if enable_model-checking is true */
 #cmakedefine MMALLOC_WANT_OVERRIDE_LEGACY @MMALLOC_WANT_OVERRIDE_LEGACY@
 /* Indicates that we have NS3 support */
 #cmakedefine HAVE_NS3 @HAVE_NS3@
 
-/* Define to 1 if you have the <inttypes.h> header file. */
-#cmakedefine HAVE_INTTYPES_H @HAVE_INTTYPES_H@
-
 /* defines whether Lua bindings must be compiled or not */
 #cmakedefine HAVE_LUA @HAVE_LUA@
 
 /* Define to 1 if you have the `makecontext' function. */
 #cmakedefine HAVE_MAKECONTEXT @HAVE_MAKECONTEXT@
 
-/* Define to 1 if you have the <memory.h> header file. */
-#cmakedefine HAVE_MEMORY_H @HAVE_MEMORY_H@
-
 /* Define if pthread_mutex_timedlock() is avaible or not (part of XPG6
    standard only?) */
 #cmakedefine HAVE_MUTEX_TIMEDLOCK @HAVE_MUTEX_TIMEDLOCK@
 /* Define to 1 if you have the `popen' function. */
 #cmakedefine HAVE_POPEN @HAVE_POPEN@
 
-/* Define to 1 if you have the <pthread.h> header file. */
-#cmakedefine HAVE_PTHREAD_H @HAVE_PTHREAD_H@
+/* Define to 1 if threads are usable . */
+#cmakedefine HAVE_PTHREAD @HAVE_PTHREAD@
 
 /* Define to 1 if you have the `readv' function. */
 #cmakedefine HAVE_READV @HAVE_READV@
 /* Define to 1 if you have the <stdint.h> header file. */
 #cmakedefine HAVE_STDINT_H @HAVE_STDINT_H@
 
-/* Define to 1 if you have the <stdlib.h> header file. */
-#cmakedefine HAVE_STDLIB_H @HAVE_STDLIB_H@
-
-/* Define to 1 if you have the <strings.h> header file. */
-#cmakedefine HAVE_STRINGS_H @HAVE_STRINGS_H@
-
 /* Define to 1 if you have the <string.h> header file. */
 #cmakedefine HAVE_STRING_H @HAVE_STRING_H@
 
 /* Define to 1 if you have the `sysconf' function. */
 #cmakedefine HAVE_SYSCONF @HAVE_SYSCONF@
 
-/* Define to 1 if you have the <sys/socket.h> header file. */
-#cmakedefine HAVE_SYS_SOCKET_H @HAVE_SYS_SOCKET_H@
-
 /* Define to 1 if you have the <sys/stat.h> header file. */
 #cmakedefine HAVE_SYS_STAT_H @HAVE_SYS_STAT_H@
 
 /* Define to 1 if you have the <windows.h> header file. */
 #cmakedefine HAVE_WINDOWS_H @HAVE_WINDOWS_H@
 
-/* Define to 1 if you have the <winsock2.h> header file. */
-#cmakedefine HAVE_WINSOCK2_H @HAVE_WINSOCK2_H@
-
-/* Define to 1 if you have the <winsock.h> header file. */
-#cmakedefine HAVE_WINSOCK_H @HAVE_WINSOCK_H@
-
 /* Define to the sub-directory in which libtool stores uninstalled libraries.*/
 #cmakedefine LT_OBJDIR @LT_OBJDIR@
 
 /* Define to 1 if you have the ANSI C header files. */
 #cmakedefine STDC_HEADERS @STDC_HEADERS@
 
-/* Define to 1 if you can safely include both <sys/time.h> and <time.h>. */
-#cmakedefine TIME_WITH_SYS_TIME @TIME_WITH_SYS_TIME@
-
 /* Tracking of latency bound */
 #cmakedefine HAVE_LATENCY_BOUND_TRACKING @HAVE_LATENCY_BOUND_TRACKING@
 
index 86d2940..edcab03 100644 (file)
@@ -6,7 +6,12 @@
 
 #include <stdio.h>
 
-__thread int thread_specific_variable = 0;
+#ifdef _MSC_VER
+__declspec(thread)
+#else 
+__thread 
+#endif
+int thread_specific_variable = 0;
 
 int main(void) {
 
index b5b7d82..d14ce09 100755 (executable)
@@ -1,4 +1,4 @@
-#! /usr/bin/perl
+#! /usr/bin/env perl
 
 # Copyright (c) 2010, 2014. The SimGrid Team.
 # All rights reserved.
index f9f58d2..7d23af0 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2005, 2012-2014. The SimGrid Team.
 # All rights reserved.
@@ -6,6 +6,8 @@
 # This program is free software; you can redistribute it and/or modify it
 # under the terms of the license (GNU LGPL) which comes with this package.
 
+use warnings;
+
 ($#ARGV >= 1) or die "Usage: index_create.pl <input-tag-file> <output-doc-file>";
 
 my($type) = "";
diff --git a/tools/doxygen/list_routing_models_examples.sh b/tools/doxygen/list_routing_models_examples.sh
new file mode 100755 (executable)
index 0000000..7bc3b5e
--- /dev/null
@@ -0,0 +1,12 @@
+#!/bin/sh
+
+cd $(dirname $0)/../../
+
+# -R -- we want to search recursively
+# -l -- only filenames, nothing else
+# $1 -- argument to this script, name of the routing model (e.g., "Floyd")
+# .  -- search in the examples folder and search EVERYTHING
+# --include -- but only include results that end in ".xml" 
+grep -R -l "$1" examples/ --include "*.xml"
+
+exit 0
index 40f60ee..ba13f8a 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl
+#!/usr/bin/env perl
 
 # Copyright (c) 2008, 2010, 2012-2014. The SimGrid Team.
 # All rights reserved.
index 2164ff2..984287c 100755 (executable)
@@ -22,7 +22,7 @@ cat - > src/mc/mc_dwarf_tagnames.cpp <<EOF
  *  \param tag tag code (see the DWARF specification)
  *  \return name of the tag
  */
-XBT_INTERNAL
+XBT_PRIVATE
 const char *MC_dwarf_tagname(int tag)
 {
   switch (tag) {
index b62d22a..11336b0 100644 (file)
@@ -1,5 +1,3 @@
-cmake_minimum_required(VERSION 2.6)
-
 set(EXECUTABLE_OUTPUT_PATH "${CMAKE_BINARY_DIR}/bin")
 
 add_executable(graphicator graphicator.c)
index ed9d31b..8ea4497 100644 (file)
@@ -11,7 +11,6 @@
 
 + \.classpath
 + \.cproject
-+ \.gitignore
 + \.project
 + \.travis.yml
 + appveyor.yml
@@ -19,7 +18,7 @@
 + README\.(coding|git)
 + mk_win-dist.sh
 
-+ buildtools/(jenkins|pipol)/.*
++ tools/jenkins/.*
 
 + contrib/.*
 
index c200c49..d18f223 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2013-2014. The SimGrid Team.
 # All rights reserved.
@@ -14,11 +14,11 @@ import zipfile
 import tempfile
 import os, sys, re
 
-dists = ['https://ci.inria.fr/simgrid/job/SimGrid-Multi/build_mode=Debug,label=%s/lastSuccessfulBuild/artifact/build/SimGrid-3.11/simgrid_full.jar'%dist
+dists = ['https://ci.inria.fr/simgrid/job/SimGrid-Multi/build_mode=Debug,label=%s/lastSuccessfulBuild/artifact/build/SimGrid-3.11/simgrid.jar'%dist
          for dist in ["small-debian-32"
                      ,"small-debian-64"
                      ,"small-freebsd-64-clang"]]
-dists.append('https://ci.inria.fr/simgrid/job/Simgrid-Mult-Win7/build_mode=Debug,label=windows-64/lastSuccessfulBuild/artifact/build/simgrid_full.jar')
+dists.append('https://ci.inria.fr/simgrid/job/Simgrid-Mult-Win7/build_mode=Debug,label=windows-64/lastSuccessfulBuild/artifact/build/simgrid.jar')
 
 class SimJar(object):
   def __init__(self, filename='simgrid.jar'):
index 5ab5958..7ff91da 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl
+#!/usr/bin/env perl
 
 # Copyright (c) 2013-2015. The SimGrid Team.
 # All rights reserved.
@@ -13,6 +13,7 @@
 # Copyright 2003, Dan Kegel.  Licensed under GPL.  See the file ../COPYING for details.
 
 use strict;
+use warnings;
 
 die "Please install iamerican to use that script." 
   unless (-r "/usr/lib/ispell/american.hash");
similarity index 79%
rename from buildtools/jenkins/run_DynamicAnalysis.sh
rename to tools/jenkins/DynamicAnalysis.sh
index 6f11138..89e07a2 100755 (executable)
@@ -18,6 +18,27 @@ do_cleanup() {
   find $WORKSPACE -name "memcheck_test_*.memcheck" -exec rm {} \;
 }
 
+### Check the node installation
+
+for pkg in xsltproc valgrind 
+do
+   if dpkg -l |grep -q $pkg 
+   then 
+      echo "$pkg is installed. Good."
+   else 
+      die "please install $pkg before proceeding" 
+   fi
+done
+
+if [ -e /usr/local/gcovr-3.1/scripts/gcovr ] 
+then
+  echo "gcovr is installed, good."
+else
+  die "Please install /usr/local/gcovr-3.1/scripts/gcovr"
+fi
+
+### Cleanup previous runs
+
 ! [ -z "$WORKSPACE" ] || die "No WORKSPACE"
 [ -d "$WORKSPACE" ] || die "WORKSPACE ($WORKSPACE) does not exist"
 
@@ -30,6 +51,8 @@ done
 
 cd $WORKSPACE/build
 
+### Proceed with the tests
+
 cmake -Denable_documentation=OFF -Denable_lua=OFF -Denable_tracing=ON \
       -Denable_compile_optimizations=OFF -Denable_compile_warnings=ON -Denable_lib_static=OFF \
       -Denable_latency_bound_tracking=OFF -Denable_jedule=OFF -Denable_mallocators=OFF \
@@ -65,7 +88,7 @@ ctest -D ExperimentalCoverage || true
 
 if [ -f Testing/TAG ] ; then
    /usr/local/gcovr-3.1/scripts/gcovr -r .. --xml-pretty -o $WORKSPACE/xml_coverage.xml
-   xsltproc $WORKSPACE/buildtools/jenkins/ctest2junit.xsl Testing/`head -n 1 < Testing/TAG`/Test.xml > CTestResults_memcheck.xml
+   xsltproc $WORKSPACE/tools/jenkins/ctest2junit.xsl Testing/`head -n 1 < Testing/TAG`/Test.xml > CTestResults_memcheck.xml
    mv CTestResults_memcheck.xml $WORKSPACE
 fi
 
similarity index 90%
rename from buildtools/jenkins/build.sh
rename to tools/jenkins/build.sh
index a853ee3..acbb39c 100755 (executable)
@@ -7,6 +7,16 @@
 
 set -e
 
+# Cleanup previous attempts
+rm -rf /tmp/simgrid*tmp
+rm -rf /tmp/surf-java*tmp
+
+# Help older cmakes
+if [ -e /usr/lib/jvm/java-7-openjdk-amd64 ] ; 
+then
+  export JAVA_HOME=/usr/lib/jvm/java-7-openjdk-amd64
+fi
+
 # usage: die status message...
 die () {
   local status=${1:-1}
@@ -112,7 +122,7 @@ echo "XX"
 
 ctest -T test --output-on-failure --no-compress-output || true
 if [ -f Testing/TAG ] ; then
-   xsltproc $WORKSPACE/buildtools/jenkins/ctest2junit.xsl Testing/`head -n 1 < Testing/TAG`/Test.xml > CTestResults.xml
+   xsltproc $WORKSPACE/tools/jenkins/ctest2junit.xsl Testing/`head -n 1 < Testing/TAG`/Test.xml > CTestResults.xml
    mv CTestResults.xml $WORKSPACE
 fi
 
index 04049fa..ba78a80 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/python
+#!/usr/bin/env python
 
 # Copyright (c) 2013-2014. The SimGrid Team.
 # All rights reserved.
index 1c29e79..6502ccf 100755 (executable)
@@ -1,4 +1,4 @@
-#! /usr/bin/perl
+#! /usr/bin/env perl
 
 # Copyright (c) 2005-2012, 2014. The SimGrid Team.
 # All rights reserved.
index 1a66dd3..46446cb 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/ruby
+#!/usr/bin/env ruby
 # Wrapper around the real `as` which adds filtering capabilities.
 
 require "tempfile"
index a2f91aa..64e7990 100755 (executable)
@@ -1,9 +1,10 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 # Transform assembly in order to clean each stack frame for X86_64.
 
 use strict;
-$SIG{__WARN__} = sub { die @_ };
+use warnings;
 
+$SIG{__WARN__} = sub { die @_ };
 
 # Whether we are still scanning the content of a function:
 our $scanproc = 0;
index 8b8a62f..62504af 100755 (executable)
@@ -1,7 +1,9 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 # Compiler wrapper with stack-cleaner support (enabled by default).
 # Usage: ./compiler-wrapper target-compiler args [-f[no-]stack-cleaner]
 
+use warnings;
+
 use File::Basename;
 
 my $compiler = shift(@ARGV);
index b7fa5af..b0a018c 100644 (file)
@@ -1,21 +1,19 @@
-cmake_minimum_required(VERSION 2.6)
-
 configure_file("${CMAKE_HOME_DIRECTORY}/tools/tesh/tesh.pl"
   "${CMAKE_BINARY_DIR}/bin/tesh" @ONLY IMMEDIATE)
 
-    file(COPY        ${CMAKE_HOME_DIRECTORY}/tools/cmake/Scripts/Diff.pm
+    file(COPY        ${CMAKE_HOME_DIRECTORY}/tools/cmake/scripts/Diff.pm
          DESTINATION ${CMAKE_BINARY_DIR}/bin
          FILE_PERMISSIONS OWNER_EXECUTE OWNER_WRITE OWNER_READ
                           GROUP_EXECUTE GROUP_READ)
+    file(COPY        ${CMAKE_HOME_DIRECTORY}/tools/cmake/scripts/IPC
+         DESTINATION ${CMAKE_BINARY_DIR}/bin)
 
 set(tesh_files
   ${tesh_files}
   ${CMAKE_CURRENT_SOURCE_DIR}/setenv.tesh
   ${CMAKE_CURRENT_SOURCE_DIR}/set-output-ignore.tesh
   ${CMAKE_CURRENT_SOURCE_DIR}/set-output-sort.tesh
-  ${CMAKE_CURRENT_SOURCE_DIR}/set-output-sort-1.tesh
   ${CMAKE_CURRENT_SOURCE_DIR}/set-return.tesh
-  ${CMAKE_CURRENT_SOURCE_DIR}/set-signal.tesh
   ${CMAKE_CURRENT_SOURCE_DIR}/set-timeout.tesh
   ${CMAKE_CURRENT_SOURCE_DIR}/background.tesh
   ${CMAKE_CURRENT_SOURCE_DIR}/basic.tesh
@@ -44,7 +42,5 @@ set(bin_files
   )
 set(txt_files
   ${txt_files}
-  ${CMAKE_CURRENT_SOURCE_DIR}/README
-  ${CMAKE_CURRENT_SOURCE_DIR}/tesh.1
   PARENT_SCOPE
   )
index c1be222..0f4e134 100644 (file)
@@ -5,58 +5,77 @@
 # father), so we do the test a bunch of times.
 #
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 01
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 02
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 03
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 04
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 05
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 06
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 07
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 08
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 09
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 10
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 11
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 12
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 13
+$ cmake -E echo
 
-< blablablablablablablablablablablablablablablablablablablabla
->
-$ echo
+< blablablablablablablablablablablablablablablablablablablabla 14
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 15
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 16
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 17
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 18
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 19
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 20
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 21
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 22
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 23
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 24
+$ cmake -E echo
+
+< blablablablablablablablablablablablablablablablablablablabla 25
+$ cmake -E echo
index 28be9c2..7453ff8 100644 (file)
@@ -5,58 +5,52 @@ p Order: in, out, cmd
 < < TOTO
 < > TOTO
 < $ cat
-> Enable coverage
 > Test suite from stdin
 > [(stdin):3] cat
 > Test suite from stdin OK
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
 
 p Order: out, in, cmd
 < > TOTO
 < < TOTO
 < $ cat
-> Enable coverage
 > Test suite from stdin
 > [(stdin):3] cat
 > Test suite from stdin OK
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
 
 p Order: out, cmd, in
 < > TOTO
 < $ cat
 < < TOTO
-> Enable coverage
 > Test suite from stdin
 > [(stdin):2] cat
 > Test suite from stdin OK
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
 
 p Order: in, cmd, out
 < < TOTO
 < $ cat
 < > TOTO
-> Enable coverage
 > Test suite from stdin
 > [(stdin):2] cat
 > Test suite from stdin OK
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
 
 p Order: cmd, out, in
 < $ cat
 < > TOTO
 < < TOTO
-> Enable coverage
 > Test suite from stdin
 > [(stdin):1] cat
 > Test suite from stdin OK
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
 
 p Order: cmd, in, out
 < $ cat
 < < TOTO
 < > TOTO
-> Enable coverage
 > Test suite from stdin
 > [(stdin):1] cat
 > Test suite from stdin OK
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
diff --git a/tools/tesh/README b/tools/tesh/README
deleted file mode 100644 (file)
index 5298b49..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-This is the TESH tool. It constitutes a testing shell, ie a sort of shell
-specialized to run tests. The list of actions to take is parsed from files
-files called testsuite.
-
-Testsuites syntax
------------------
-Here is the syntax of these files:
-
-The kind of each line is given by the first char (the second char should be
-blank and is ignored):
-
- `$' command to run in foreground
- `&' command to run in background
- `<' input to pass to the command
- `>' output expected from the command
- `!' metacommand, which can be one of:
-     `timeout' <integer>|no
-     `expect signal' <signal name>
-     `expect return' <integer>
-     `output' <ignore|display>
-     `setenv <key>=<val>'
- `p' a string to print
- `P' a string to print at the CRITICAL level (ease logging grepping)
-
-If the expected output do not match what the command spits, TESH will produce
-an error showing the diff (see OUTPUT below).
-
-Command line arguments
-----------------------
-Tesh accepts several command line arguments:
-  --cd some/directory : ask tesh to switch the working directory before
-                        launching the tests
-  --setenv var=value  : set a specific environment variable
-  --cfg arg           : add parameter --cfg=arg to each command line
-  --enable-coverage   : ignore output lines starting with "profiling:"
-
-IO orders
----------
-
-The < and > lines add IO to the command defined in the current block (blocks
-are separated by blank lines). It is possible to place these lines either after
-the command or before. The difference between the two following chunks is
-mainly cosmetic in your testsuites, TESH don't care. (cf IO-orders.tesh)
-
- $ cat
- < TOTO
- > TOTO
-
- > TOTO
- $ cat
- < TOTO
-
-Nevertheless, it is possible to have several commands in the same block, but
-none of them can have any output. It may seem a bit restrictive, as one could
-say that a command gets all the IO until the next command, but I'm afraid of
-errors such as the following:
-
- $ cd toto
- > TOTO
- $ mkfile file
-
-TOTO will be passed to the cd command, where the user clearly want to pass it
-to the mkfile built-in command (see below).
-
-Stream redirection
-------------------
-Stream redirections (">", "<" and "|" constructs in sh) are not
-implemented yet in tesh. This is a bit restrictive, but well, patch
-welcome...
-
-The situation in which it is mainly problematic is to create a
-temporary file. The solution is to use the "mkfile" built-in command,
-as in the following example:
-$ mkfile myFile
-> some content
-> to the file
-
-This will create a file called myFile (first argument of the mkfile
-command). Its content will be all the input provided to the command.
-
-RETURN CODE
------------
-
-TESH spits an appropriate error message when the child do not return 0 as
-return code (cf. catch-return.tesh), and returns code+40 itself.
-
-It is also possible to specify that a given command must return another
-value. For this, use the "expect return" metacommand, which takes an integer as
-argument. The change only apply to the next command (cf. set-return.tesh).
-
-SIGNALS
--------
-
-TESH detects when the child is killed by a signal (like on segfaults), and
-spits an appropriate error message (cf. catch-signal.tesh).
-
-It is also possible to specify that a given command must raise a given
-signal. For this, use the "expect signal" metacommand. It takes the signal name
-as argument. The change only apply to the next command (cf. set-signal.tesh).
-
-TIMEOUTS
---------
-
-By default, all commands are given 5 seconds to execute
-(cf. catch-timeout.tesh). You can change this with the "timeout", which
-takes an integer as argument. The change only apply to the next command
-(cf. set-timeout.tesh). If you pass "no" as argument, the command
-cannot timeout.
-
-OUTPUT
-------
-
-By default, the commands output is matched against the one expected,
-and an error is raised on discrepancy. Metacommands to change this:
- "output ignore"  -> output completely discarded
- "output display" -> output displayed (but not verified)
- "output sort"    -> sorts the display before verifying it (see below)
-
-SORTING OUTPUT
---------------
-Sorting the output seems to be a strange idea, but it is mandatory in
-SimGrid since the processes run out of order at any scheduling point
-(ie, every processes ready to run at simulated time t run in
-parallel). To ensure that the simulator outputs still match, we have
-to sort the output back before comparing it.
-
-We expect the simulators to run with that log formatting argument:
-   -log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n
-Then, tesh sorts string on the 19 first chars only, and is stable when
-line beginnings are equal. This should ensure that:
- (1) tesh is effective (no false positive, no false negative)
- (2) scheduling points are separated from each other
- (3) at each scheduling point, processes are separated from each other
- (4) the order of what a given process says at a given scheduling
-     point is preserved.
-
-This is of course very SimGrid oriented, breaking the generality of
-tesh, but who cares, actually?
-
-If you want to change the length of the prefix used for the sort,
-simply specify it after the output sort directive, like this:
-
-! output sort 22
-
-ENVIRONMENT
------------
-You can add some content to the tested processes environment with the
-setenv metacommand. It works as expected. For example:
-  "setenv PATH=/bin"
\ No newline at end of file
index 1029d89..3fbabd3 100644 (file)
@@ -1,51 +1,20 @@
 
-$ rm -rf temp_testdir_background
+$ cmake -E remove_directory temp_testdir_background
 $ mkdir temp_testdir_background
 $ cd temp_testdir_background
 
-< #include <unistd.h>
-< #include <stdlib.h>
-< #include <stdio.h>
-< #include <sys/types.h>
-< #include <sys/stat.h>
-< #include <fcntl.h>
-< #ifdef WIN32 
-<   #include "windows.h"
-< #endif
-<                   
-< int main() {
-<   char buff[2048];
-<   int got;
-<   int in;
+< use strict; 
+< sleep(2);
+< open (FILE, "<tmp_fich") || die "Cannot open tmp_fich: $!\n";
 < 
-< #ifndef WIN32 
-<   sleep(1);
-< #else
-<   Sleep(1000);
-< #endif
-<   in = open("tmp_fich",O_RDONLY|O_CREAT);
-<   if (in == -1) {
-<     perror("Cannot open tmp_fich: ");
-<     exit(1);
-<   }
-<   while ((got = read(in,&buff,2048))>0) {
-<      int w = write(1,&buff,got);
-<      if (w<0) {
-<        perror("Error while writing:");
-<        exit(1);
-<      }
-<   }
-<   if (got < 0) {
-<     perror("Error while reading:");
-<     exit(1);
-<   }
-<   return 0;
+< while (<FILE>) {
+<   print;
 < }
-$ mkfile delayed_cat.c
+< exit 0;
+<
+$ mkfile delayed_cat.pl
 
-$ cc -Wall -o delayed_cat delayed_cat.c
-
-& ./delayed_cat
+& perl delayed_cat.pl
 > TOTO
 
 < TOTO
@@ -53,4 +22,4 @@ $ mkfile tmp_fich
 
 $ sleep 2
 $ cd ..
-$ rm -rf temp_testdir_background
+$ cmake -E remove_directory temp_testdir_background
index 32289af..7f3d8c6 100644 (file)
@@ -13,7 +13,7 @@ $ cat tmp_fich
 ! output ignore
 < $ cat tmp_fich
 < > TUTU TOTO
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh 
 
 $ rm tmp_fich
 
@@ -77,14 +77,14 @@ $ sed 's/_/ /'
 < < _x
 < $ sed 's/_/ /'
 < > x
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh
 
 ! expect return 2
 ! output ignore
 < < x
 < $ cat
 < >  x
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh
 
 p * trailing spaces...
 < x_
@@ -96,14 +96,14 @@ $ sed 's/_/ /'
 < < x_
 < $ sed 's/_/ /'
 < > x
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh
 
 ! expect return 2
 ! output ignore
 < < x
 < $ cat
 < > x 
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh
 
 p * empty lines...
 < a
@@ -122,7 +122,7 @@ $ cat
 < $ cat
 < > a
 < > c
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh 
 
 ! expect return 2
 ! output ignore
@@ -132,7 +132,7 @@ $ ${bindir:=.}/tesh --enable-coverage
 < > a
 < >
 < > c
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh 
 
 <
 < b
@@ -150,7 +150,7 @@ $ cat
 < $ cat
 < > b
 < > c
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh 
 
 ! expect return 2
 ! output ignore
@@ -160,4 +160,4 @@ $ ${bindir:=.}/tesh --enable-coverage
 < >
 < > b
 < > c
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh 
index ff9c3d5..2179eaa 100644 (file)
@@ -2,20 +2,15 @@
 # This suite builds and uses a program raising a segfault, ie a program dying
 # of SIGSEV. tesh must detect this condition and report the issue.
 
-$ rm -rf temp_testdir-bg-set-signal
+$ cmake -E remove_directory temp_testdir-bg-set-signal
 $ mkdir temp_testdir-bg-set-signal
 
 $ cd temp_testdir-bg-set-signal
-< #include <stdlib.h>
-< int main(void) {
-<   char *A=NULL;
-<   *A = 1;
-< }
-$ mkfile segfault.c
+< kill 'SEGV', $$;
+$ mkfile segfault.pl
 
-$ cc -o segfault segfault.c
 ! expect signal SIGSEGV
-& ./segfault
-$ sleep 1
+& perl segfault.pl
+
 $ cd ..
-$ rm -rf temp_testdir-bg-set-signal
+$ cmake -E remove_directory temp_testdir-bg-set-signal
index f9d21a2..3a96bf0 100644 (file)
@@ -2,27 +2,10 @@
 # This suite builds and uses a program returning 1.
 # tesh must detect this condition and report the issue.
 
-$ rm -rf temp_testdir-catch-return
-$ mkdir temp_testdir-catch-return
-
-$ cd temp_testdir-catch-return
-< #include <stdlib.h>
-< int main(void) {
-<   exit(1);
-< }
-$ mkfile return1.c
-
-$ cc -o return1 return1.c
-
 ! expect return 41
-< $ ./return1
-$ ../tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
-> Enable coverage
+< $ perl -e "exit 1"
+$ perl ${bindir:=.}/tesh
 > Test suite from stdin
-> [(stdin):1] ./return1
+> [(stdin):1] perl -e "exit 1"
 > Test suite `(stdin)': NOK (<(stdin):1> returned code 1)
-> Output of <(stdin):1> so far:
-> ||
-
-$ cd ..
-$ rm -rf temp_testdir-catch-return
+> <(stdin):1> No output so far.
index 64d37e8..be19f34 100644 (file)
@@ -2,28 +2,25 @@
 # This suite builds and uses a program raising a segfault, ie a program dying
 # of SIGSEV. tesh must detect this condition and report the issue.
 
-$ rm -rf temp_testdir-catch-signal
+$ cmake -E remove_directory temp_testdir-catch-signal
 $ mkdir temp_testdir-catch-signal
 
 $ cd temp_testdir-catch-signal
-< #include <stdlib.h>
-< int main(void) {
-<   char *A=NULL;
-<   *A = 1;
-< }
-$ mkfile segfault.c
+< kill 'SEGV', $$;
+$ mkfile segfault.pl
 
-$ cc -o segfault segfault.c
+p Check that we notice when SEGV is raised
+! expect signal SIGSEGV
+$ perl segfault.pl
 
+p Check that we return the expected return value on SEGV
 ! expect return 15
-< $ ./segfault
-$ ../tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
-> Enable coverage
+< $ perl segfault.pl
+$ perl ${bindir:=.}/tesh
 > Test suite from stdin
-> [(stdin):1] ./segfault
+> [(stdin):1] perl segfault.pl
 > Test suite `(stdin)': NOK (<(stdin):1> got signal SIGSEGV)
-> Output of <(stdin):1> so far:
-> ||
+> <(stdin):1> No output so far.
 
 $ cd ..
-$ rm -rf temp_testdir-catch-signal
+$ cmake -E remove_directory temp_testdir-catch-signal
index d9daf92..00c5ff6 100644 (file)
@@ -6,10 +6,8 @@
 ! expect return 3
 < ! timeout 1
 < $ sleep 6
-> Enable coverage
 > Test suite from stdin
 > [(stdin):2] sleep 6
-> <(stdin):2> timeouted. Kill the process.
-> <(stdin):2> No output before timeout
 > Test suite `(stdin)': NOK (<(stdin):2> timeout after 1 sec)
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+> <(stdin):2> No output so far.
+$ perl ${bindir:=.}/tesh
index e60d760..1dcd26d 100644 (file)
@@ -6,8 +6,7 @@ p This tests whether TESH detects wrong outputs
 < > TOTO
 < < TUTU
 < $ cat
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
-> Enable coverage
+$ perl ${bindir:=.}/tesh
 > Test suite from stdin
 > [(stdin):3] cat
 > Output of <(stdin):3> mismatch:
index dc297db..db9137e 100644 (file)
@@ -2,7 +2,7 @@
 
 # This example uses the cd command
 
-$ rm -rf testdir_temp-cd
+$ cmake -E remove_directory testdir_temp-cd
 $ mkdir testdir_temp-cd
 $ cd testdir_temp-cd
 
@@ -12,15 +12,14 @@ $ ls
 # Check that tesh detects properly cd to non-existing directories
 ! expect return 4
 < $ cd toto
-> Enable coverage
 > Test suite from stdin
 > Chdir to toto failed: No such file or directory
 > Test suite `(stdin)': NOK (system error)
-$ ../tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
+$ perl ${bindir:=.}/tesh
 
 # The next command checks that there is a testdir_temp-cd in the upper directory,
 # ie that mkdir and cd both worked.
 $ test -e ../testdir_temp-cd
 
 $ cd ..
-$ rmdir testdir_temp-cd
+$ cmake -E remove_directory testdir_temp-cd
index 9cc8d18..88b1f55 100755 (executable)
@@ -1,4 +1,4 @@
-#!/usr/bin/perl -w
+#!/usr/bin/env perl
 
 # Copyright (c) 2010, 2014. The SimGrid Team.
 # All rights reserved.
@@ -6,6 +6,8 @@
 # This program is free software; you can redistribute it and/or modify it
 # under the terms of the license (GNU LGPL) which comes with this package.
 
+use warnings;
+
 use Term::ANSIColor qw{:constants};
 $Term::ANSIColor::AUTORESET = 1;
 
index 1fba401..120b620 100644 (file)
@@ -6,8 +6,7 @@ p This tests whether TESH accepts to ignore command output
 < > TOTO
 < < TUTU
 < $ cat
-$ ./tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n'
-> Enable coverage
+$ perl ${bindir:=.}/tesh
 > Test suite from stdin
 > [(stdin):4] cat
 > (ignoring the output of <(stdin):4> as requested)
diff --git a/tools/tesh/set-output-sort-1.tesh b/tools/tesh/set-output-sort-1.tesh
deleted file mode 100644 (file)
index c009b4a..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-p Test sorting and filtering of output
-
-$ true
-
-! output sort
-$ true
-
-$ printf 'profiling: foo\\n'
-
-$ printf 'profiling: foo'
-
-! output sort
-$ printf 'profiling: foo\\n'
-
-! output sort
-$ printf 'profiling: foo'
-
-$ printf 'a\\nb\\nc\\nd\\n'
-> a
-> b
-> c
-> d
-
-$ printf 'a\\nb\\nc\\nd'
-> a
-> b
-> c
-> d
-
-! output sort
-$ printf 'c\\nd\\nb\\na\\n'
-> a
-> b
-> c
-> d
-
-! output sort
-$ printf 'c\\nd\\nb\\na'
-> a
-> b
-> c
-> d
-
-$ printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz\\n'
-> a
-> b
-> c
-> d
-
-$ printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz'
-> a
-> b
-> c
-> d
-
-! output sort
-$ printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz\\n'
-> a
-> b
-> c
-> d
-
-! output sort
-$ printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz'
-> a
-> b
-> c
-> d
index b7ae307..f0abb75 100644 (file)
@@ -2,25 +2,93 @@
 
 p This tests whether TESH correctly sorts command output
 
-$ ${bindir:=.}/tesh --enable-coverage --log='log.thresh:info tesh.fmt:%m%n' set-output-sort-1.tesh
+< p Test sorting and filtering of output
+< 
+< $ true
+< 
+< ! output sort
+< $ true
+< 
+< $ printf 'profiling: foo\\n'
+< 
+< $ printf 'profiling: foo'
+< 
+< ! output sort
+< $ printf 'profiling: foo\\n'
+< 
+< ! output sort
+< $ printf 'profiling: foo'
+< 
+< $ printf 'a\\nb\\nc\\nd\\n'
+< > a
+< > b
+< > c
+< > d
+< 
+< $ printf 'a\\nb\\nc\\nd'
+< > a
+< > b
+< > c
+< > d
+< 
+< ! output sort
+< $ printf 'c\\nd\\nb\\na\\n'
+< > a
+< > b
+< > c
+< > d
+< 
+< ! output sort
+< $ printf 'c\\nd\\nb\\na'
+< > a
+< > b
+< > c
+< > d
+< 
+< $ printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz\\n'
+< > a
+< > b
+< > c
+< > d
+< 
+< $ printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz'
+< > a
+< > b
+< > c
+< > d
+< 
+< ! output sort
+< $ printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz\\n'
+< > a
+< > b
+< > c
+< > d
+< 
+< ! output sort
+< $ printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz'
+< > a
+< > b
+< > c
+< > d
+$ perl ${bindir:=.}/tesh --enable-coverage
 > Enable coverage
-> Test suite `set-output-sort-1'
-> [set-output-sort-1:1] Test sorting and filtering of output
-> [set-output-sort-1:3] true
-> [set-output-sort-1:6] true
-> [set-output-sort-1:8] printf 'profiling: foo\\n'
-> [set-output-sort-1:10] printf 'profiling: foo'
-> [set-output-sort-1:13] printf 'profiling: foo\\n'
-> [set-output-sort-1:16] printf 'profiling: foo'
-> [set-output-sort-1:18] printf 'a\\nb\\nc\\nd\\n'
-> [set-output-sort-1:24] printf 'a\\nb\\nc\\nd'
-> [set-output-sort-1:31] printf 'c\\nd\\nb\\na\\n'
-> [set-output-sort-1:38] printf 'c\\nd\\nb\\na'
-> [set-output-sort-1:44] printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz\\n'
-> [set-output-sort-1:50] printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz'
-> [set-output-sort-1:57] printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz\\n'
-> [set-output-sort-1:64] printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz'
-> Test suite `set-output-sort-1' OK
+> Test suite from stdin
+> [(stdin):1] Test sorting and filtering of output
+> [(stdin):3] true
+> [(stdin):6] true
+> [(stdin):8] printf 'profiling: foo\\n'
+> [(stdin):10] printf 'profiling: foo'
+> [(stdin):13] printf 'profiling: foo\\n'
+> [(stdin):16] printf 'profiling: foo'
+> [(stdin):18] printf 'a\\nb\\nc\\nd\\n'
+> [(stdin):24] printf 'a\\nb\\nc\\nd'
+> [(stdin):31] printf 'c\\nd\\nb\\na\\n'
+> [(stdin):38] printf 'c\\nd\\nb\\na'
+> [(stdin):44] printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz\\n'
+> [(stdin):50] printf 'a\\nprofiling: foo\\nprofiling: bar\\nb\\nc\\nd\\nprofiling: baz'
+> [(stdin):57] printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz\\n'
+> [(stdin):64] printf 'c\\nprofiling: foo\\nprofiling: bar\\nd\\nb\\na\\nprofiling: baz'
+> Test suite from stdin OK
 
 p Check the Right Prefix Length (19) for "output sort"
 ! output sort 19
@@ -45,7 +113,7 @@ $ cat
 < $ cat
 < > 123456789012345678 A line
 < > 123456789012345678 B line
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh 
 
 p Check user-defined prefix length for "output sort"
 ! output sort 5
@@ -70,4 +138,4 @@ $ cat
 < $ cat
 < > 000 A line
 < > 000 B line
-$ ${bindir:=.}/tesh --enable-coverage
+$ perl ${bindir:=.}/tesh
index 679234d..4ff5698 100644 (file)
@@ -2,19 +2,8 @@
 # This suite builds and uses a program returning 1.
 # tesh is instructed of this return code and must not whine.
 
-$ rm -rf temp_testdir-set-return
-$ mkdir temp_testdir-set-return
-
-$ cd temp_testdir-set-return
-< #include <stdlib.h>
-< int main(void) {
-<   exit(1);
-< }
-$ mkfile return1.c
-
-$ cc -o return1 return1.c
-
 ! expect return 1
-$ ./return1
-$ cd ..
-$ rm -rf temp_testdir-set-return
+$ perl -e "exit 1"
+
+! expect return 42
+$ perl -e "exit 42"
diff --git a/tools/tesh/set-signal.tesh b/tools/tesh/set-signal.tesh
deleted file mode 100644 (file)
index 314b7f0..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#! ./tesh
-# This suite builds and uses a program raising a segfault, ie a program dying
-# of SIGSEV. tesh must detect this condition and report the issue.
-
-$ rm -rf temp_testdir-set-signal
-$ mkdir temp_testdir-set-signal
-
-$ cd temp_testdir-set-signal
-< #include <stdlib.h>
-< int main(void) {
-<   char *A=NULL;
-<   *A = 1;
-< }
-$ mkfile segfault.c
-
-$ cc -o segfault segfault.c
-! expect signal SIGSEGV
-$ ./segfault
-$ cd ..
-$ rm -rf temp_testdir-set-signal
index 7f94ed9..1ba153f 100644 (file)
@@ -5,3 +5,6 @@
 
 ! timeout 10
 $ sleep 6
+
+! timeout no
+$ sleep 1
\ No newline at end of file
index 632fd8b..dfb415e 100644 (file)
@@ -2,30 +2,16 @@
 # This suite builds and uses a program returning 1.
 # tesh is instructed of this return code and must not whine.
 
-$ rm -rf temp_testdir-setenv
-$ mkdir temp_testdir-setenv
+$ cmake -E remove_directory temp_testdir_setenv
+$ mkdir temp_testdir_setenv
+$ cd temp_testdir_setenv
 
-$ cd temp_testdir-setenv
-
-< #include <string.h>
-< #include <stdio.h>
-< extern char **environ;
-< int main(void) {
-<   char **env_iter=environ;
-<   while (*env_iter) {
-<     if (!strncmp(*env_iter,"tesh_test_toto=",strlen("tesh_test_toto=")))
-<       printf("%s\n",*env_iter);
-<     env_iter++;
-<   }
-<   return 0;
-< }
-$ mkfile getenv.c
-
-$ cc -o getenv getenv.c -g
+< print "tesh_test_toto=$ENV{tesh_test_toto}";
+$ mkfile testenv.pl
 
 ! setenv tesh_test_toto=blah
-$ ./getenv
+$ perl testenv.pl
 > tesh_test_toto=blah
 
 $ cd ..
-$ rm -rf temp_testdir-setenv
+$ cmake -E remove_directory temp_testdir_setenv
diff --git a/tools/tesh/tesh.1 b/tools/tesh/tesh.1
deleted file mode 100644 (file)
index 3c55b70..0000000
+++ /dev/null
@@ -1,148 +0,0 @@
-.\" Manpage for tesh, the TEsting SHell.
-.\" 
-.\" To read it locally (when not installed): 
-.\"   man ./tesh.1
-.\"
-.TH tesh 1 "10 Oct 2012" "1.0" "tesh man page"
-.SH NAME
-tesh \- testing shell
-.SH SYNOPSIS
-.B tesh
-[\fIOPTION\fR]... [\fIFILE\fR]...
-.SH DESCRIPTION
-This is the TESH tool. It constitutes a testing shell, ie a sort of shell specialized to run tests. The list of actions to take is parsed from files files called testsuite.
-.SH OPTIONS
-  --cd some/directory : ask tesh to switch the working directory before
-                        launching the tests
-  --setenv var=value  : set a specific environment variable
-  --cfg arg           : add parameter --cfg=arg to each command line
-  --enable-coverage   : ignore output lines starting with "profiling:"
-.SH TESH FILE SYNTAX
-Here is the syntax of these files:
-
-The kind of each line is given by the first char (the second char should be
-blank and is ignored):
-
- `$' command to run in foreground
- `&' command to run in background
- `<' input to pass to the command
- `>' output expected from the command
- `!' metacommand, which can be one of:
-     `timeout' <integer>|no
-     `expect signal' <signal name>
-     `expect return' <integer>
-     `output' <ignore|display>
-     `setenv <key>=<val>'
- `p' a string to print
- `P' a string to print at the CRITICAL level (ease logging grepping)
-
-If the expected output do not match what the command spits, TESH will produce
-an error showing the diff (see OUTPUT below).
-.SH IO ORDERS
-The < and > lines add IO to the command defined in the current block (blocks
-are separated by blank lines). It is possible to place these lines either after
-the command or before. The difference between the two following chunks is
-mainly cosmetic in your testsuites, TESH don't care. (cf IO-orders.tesh)
-
- $ cat
- < TOTO
- > TOTO
-
- > TOTO
- $ cat
- < TOTO
-
-Nevertheless, it is possible to have several commands in the same block, but
-none of them can have any output. It may seem a bit restrictive, as one could
-say that a command gets all the IO until the next command, but I'm afraid of
-errors such as the following:
-
- $ cd toto
- > TOTO
- $ mkfile file
-
-TOTO will be passed to the cd command, where the user clearly want to pass it
-to the mkfile built-in command (see below).
-.SH STREAM REDIRECTION
-Stream redirections (">", "<" and "|" constructs in sh) are not
-implemented yet in tesh. This is a bit restrictive, but well, patch
-welcome...
-
-The situation in which it is mainly problematic is to create a
-temporary file. The solution is to use the "mkfile" built-in command,
-as in the following example:
-$ mkfile myFile
-> some content
-> to the file
-
-This will create a file called myFile (first argument of the mkfile
-command). Its content will be all the input provided to the command.
-.SH RETURN CODE
-TESH spits an appropriate error message when the child do not return 0 as
-return code (cf. catch-return.tesh), and returns code+40 itself.
-
-It is also possible to specify that a given command must return another
-value. For this, use the "expect return" metacommand, which takes an integer as
-argument. The change only apply to the next command (cf. set-return.tesh).
-.SH SIGNALS
-TESH detects when the child is killed by a signal (like on segfaults), and
-spits an appropriate error message (cf. catch-signal.tesh).
-
-It is also possible to specify that a given command must raise a given
-signal. For this, use the "expect signal" metacommand. It takes the signal name
-as argument. The change only apply to the next command (cf. set-signal.tesh).
-.SH TIMEOUTS
-By default, all commands are given 5 seconds to execute
-(cf. catch-timeout.tesh). You can change this with the "timeout", which
-takes an integer as argument. The change only apply to the next command
-(cf. set-timeout.tesh). If you pass "no" as argument, the command
-cannot timeout.
-.SH OUTPUT
-By default, the commands output is matched against the one expected,
-and an error is raised on discrepancy. Metacommands to change this:
- "output ignore"  -> output completely discarded
- "output display" -> output displayed (but not verified)
- "output sort"    -> sorts the display before verifying it (see below)
-.SH SORTING OUTPUT
-
-SimGrid is designed to produce perfectly reproducible results, so its
-output can usualy be compared without any preprocessing. This is not
-true anymore when the user activates parallel execution: User
-processes are run in parallel at each timestamp, and the output is not
-reproducible anymore. Until you sort the lines.
-
-If you ask for 
-.B ! output sort
-then tesh will sort the whole lines. But it really complicates the
-analysis of the error detected: the logical order of the output is
-defeated by the lexicographical sort. 
-
-The solution is to ask for
-.B ! output sort 19
-instead to sort only on the prefix of the line. Indeed, we run our simulation
-tests with the flag: 
-  --log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n
-
-Then, the previous command sorts  lines on the first 19 chars, that is
-exactly the length of the prefix indicating the timestamp and the
-process. That's exactly what we need:
- - Every timestamps remain separated, as it should; 
- - In each timestamp, the output order of processes become
-   reproducible: that's the lexicographical order of their name;
- - For each process, the order of its execution is preserved: its
-   messages within a given timestamp are not reordered.
-
-That way, tesh can do its job (no false positive, no false negative)
-despite the unpredictable order of executions of processes within a
-timestamp, and reported errors remain easy to analyze (execution of a
-given process preserved).
-
-This is of course very SimGrid oriented, but could even be usable by
-others, who knows?
-
-.SH ENVIRONMENT
-You can add some content to the tested processes environment with the
-setenv metacommand. It works as expected. For example:
-  "setenv PATH=/bin"
-.SH BUGS
-No known bugs. 
index 2dd685b..54f053a 100755 (executable)
@@ -1,6 +1,6 @@
-#! /usr/bin/perl
+#! /usr/bin/env perl
 
-# Copyright (c) 2012-2014. The SimGrid Team.
+# Copyright (c) 2012-2015. The SimGrid Team.
 # All rights reserved.
 
 # This program is free software; you can redistribute it and/or modify it
@@ -8,6 +8,9 @@
 eval 'exec perl -S $0 ${1+"$@"}'
   if $running_under_some_shell;
 
+# If you change this file, please stick to the formatting you got with:
+# perltidy --backup-and-modify-in-place --maximum-line-length=180 --output-line-ending=unix --cuddled-else
+
 =encoding UTF-8
 
 =head1 NAME
@@ -16,701 +19,771 @@ tesh -- testing shell
 
 =head1 SYNOPSIS
 
-B<tesh> [I<options>] I<tesh_file>
+B<tesh> [I<options>]... I<testsuite>
+
+=head1 DESCRIPTION
+
+Tesh is the testing shell, a specialized shell for running tests. It
+provides the specified input to the tested commands, and check that
+they produce the expected output and return the expected value.
+
+=head1 OPTIONS
+
+  --cd some/directory : ask tesh to switch the working directory before
+                        launching the tests
+  --setenv var=value  : set a specific environment variable
+  --cfg arg           : add parameter --cfg=arg to each command line
+  --enable-coverage   : ignore output lines starting with "profiling:"
+
+=head1 TEST SUITE FILE SYTAX
+
+A test suite is composed of one or several I<command blocks> separated
+by empty lines, each of them being composed of a command to run, its
+input text and the expected output.
+
+The first char of each line specifies the type of line according to
+the following list. The second char of each line is ignored.
+
+ `$' command to run in foreground
+ `&' command to run in background
+
+ `<' input to pass to the command
+ `>' output expected from the command
+
+ `!' metacommand, which can be one of:
+     `timeout' <integer>|no
+     `expect signal' <signal name>
+     `expect return' <integer>
+     `output' <ignore|display>
+     `setenv <key>=<val>'
+
+ `p' an informative message to print
+
+If the expected output do not match the produced output, or if the
+command did not end as expected, Tesh provides an error message (see
+the OUTPUT section below) and stops.
+
+=head2 Command blocks examples
+
+In a given command block, you can declare the command, its input and
+its expected output in the order that you see fit.
+
+    $ cat
+    < TOTO
+    > TOTO
+
+    > TOTO
+    $ cat
+    < TOTO
+
+    > TOTO
+    < TOTO
+    $ cat
+
+You can group several commands together, provided that they don't have
+any input nor output.
+
+    $ mkdir testdir
+    $ cd testdir
+
+=head2 Enforcing the command return code
+
+By default, Tesh enforces that the tested command returns 0. If not,
+it fails with an appropriate message and returns I<code+40> itself.
+
+You specify that a given command block is expected to return another
+code as follows:
+
+    # This command MUST return 42
+    ! expect return 42
+    $ sh -e "exit 42"
+
+The I<expect return> construct applies only to the next command block.
+
+=head2 Commands that are expected to raise signals
+
+By default, Tesh detects when the command is killed by a signal (such
+as SEGV on segfaults). This is usually unexpected and unfortunate. But
+if not, you can specify that a given command block is expected to fail
+with a signal as follows:
+
+    # This command MUST raise a segfault
+    ! expect signal SIGSEGV
+    $ ./some_failing_code
+
+The I<expect signal> construct applies only to the next command block.
+
+=head2 Timeouts
+
+By default, no command is allowed to run more than 5 seconds. You can
+change this value as follows:
+
+    # Allow some more time to the command
+    ! timeout 60
+    $ ./some_longer_command
+
+You can also disable the timeout completely by passing "no" as a value:
+
+    # This command will never timeout
+    ! timeout no
+    $ ./some_very_long_but_safe_command
+
+=head2 Setting environment variables
+
+You can modify the environment of the tested commands as follows:
+
+    ! setenv PATH=/bin
+    $ my_command
+
+=head2 Not enforcing the expected output 
+
+By default, the commands output is matched against the one expected,
+and an error is raised on discrepancy. Metacommands to change this:
+
+=over 4
+
+=item output ignore
+
+The output is completely discarded.
+
+=item output display
+
+The output is displayed, but no error is issued if it differs from the
+expected output.
+
+=item output sort
+
+The output is sorted before comparison (see next section).
+
+=back
+
+=head2 Sorting output
+
+If the order of the command output changes between runs, you want to
+sort it before enforcing that it is exactly what you expect. In
+SimGrid for example, this happens when parallel execution is
+activated: User processes are run in parallel at each timestamp, and
+the output is not reproducible anymore. Until you sort the lines.
+
+You can sort the command output as follows:
+
+    ! output sort
+    $ ./some_multithreaded_command
+
+Sorting lines this ways often makes the tesh output very intricate,
+complicating the error analysis: the process logical order is defeated
+by the lexicographical sort.
+
+The solution is to prefix each line of your output with temporal
+information so that lines can be grouped by timestamps. The
+lexicographical sort then only applies to lines that occured at the
+same timestamp. Here is a SimGrid example:
+
+    # Sort only lines depending on the first 19 chars
+    ! output sort 19
+    $ ./some_simgrid_simulator --log=root.fmt:[%10.6r]%e(%i:%P@%h)%e%m%n
+
+This approach may seem surprizing at the first glance but it does its job:
+
+=over 4
+
+=item Every timestamps remain separated, as it should; 
+
+=item In each timestamp, the output order of processes become
+   reproducible: that's the lexicographical order of their name;
+
+=item For each process, the order of its execution is preserved: its
+   messages within a given timestamp are not reordered.
+
+=back
+
+That way, tesh can do its job (no false positive, no false negative)
+despite the unpredictable order of executions of processes within a
+timestamp, and reported errors remain easy to analyze (execution of a
+given process preserved).
+
+This example is very SimGrid oriented, but the feature could even be
+usable by others, who knows?
+
+
+=head1 BUILTIN COMMANDS
+
+=head2 mkfile: creating a file
+
+This command creates a file of the name provided as argument, and adds
+the content it gets as input.
+
+  $ mkfile myFile
+  > some content
+  > to the file
+
+It is not possible to use the cat command, as one would expect,
+because stream redirections are currently not implemented in Tesh.
+
+=head1 BUGS, LIMITATIONS AND POSSIBLE IMPROVEMENTS
+
+The main limitation is the lack of stream redirections in the commands
+(">", "<" and "|" shell constructs and friends). The B<mkfile> builtin
+command makes this situation bearable.
+
+It would be nice if we could replace the tesh file completely with
+command line flags when the output is not to be verified.
 
 =cut
-my($bindir)=".";
-my($srcdir)=".";
-my($timeout)=0;
-my($time_to_wait)=0;
-my $path = $0;
-my $OS;
-my $enable_coverage=0;
-my $diff_tool=0;
-my $diff_tool_tmp_fh=0;
-my $diff_tool_tmp_filename=0;
-my $sort_prefix = -1;
+
+BEGIN {
+    # Disabling IPC::Run::Debug saves tons of useless calls.
+    $ENV{'IPCRUNDEBUG'} = 'none'
+      unless exists $ENV{'IPCRUNDEBUG'};
+}
+
+my $enable_coverage        = 0;
+my $diff_tool              = 0;
+my $diff_tool_tmp_fh       = 0;
+my $diff_tool_tmp_filename = 0;
+my $sort_prefix            = -1;
 my $tesh_file;
 my $tesh_name;
-my $error=0;
-my $exitcode=0;
+my $error    = 0;
+my $exitcode = 0;
 my @bg_cmds;
 my (%environ);
 $SIG{'PIPE'} = 'IGNORE';
+
+my $path = $0;
 $path =~ s|[^/]*$||;
-push @INC,$path;
+push @INC, $path;
+
+use lib "@CMAKE_BINARY_DIR@/bin";
+
+use Diff qw(diff);    # postpone a bit to have time to change INC
 
 use Getopt::Long qw(GetOptions);
 use strict;
-use Term::ANSIColor;
 use Text::ParseWords;
-use IPC::Open3;
+use IPC::Run qw(start run timeout finish);
 use IO::File;
+use English;
 
-if($^O eq "linux"){
-    $OS = "UNIX";
-}
-else{
-    $OS = "WIN";
-    $ENV{"PRINTF_EXPONENT_DIGITS"} = "2";
-}
-
-##
-## Command line option handling
-##
+####
+#### Portability bits for windows
+####
 
-sub var_subst {
-    my ($text, $name, $value) = @_;
-    if ($value) {
-        $text =~ s/\${$name(?::[=-][^}]*)?}/$value/g;
-        $text =~ s/\$$name(\W|$)/$value$1/g;
-    }
-    else {
-        $text =~ s/\${$name:=([^}]*)}/$1/g;
-        $text =~ s/\${$name}//g;
-        $text =~ s/\$$name(\W|$)/$1/g;
-    }
-    return $text;
-}
+use constant RUNNING_ON_WINDOWS => ( $OSNAME =~ /^(?:mswin|dos|os2)/oi );
+use POSIX qw(:sys_wait_h WIFEXITED WIFSIGNALED WIFSTOPPED WEXITSTATUS WTERMSIG WSTOPSIG
+  :signal_h SIGINT SIGTERM SIGKILL SIGABRT SIGSEGV);
 
-# option handling helper subs
-sub cd_cmd {
-  my $directory=$_[1];
-  my $failure=1;
-  if (-e $directory && -d $directory) {
-    chdir("$directory");
-    print "[Tesh/INFO] change directory to $directory\n";
-  $failure=0;
-  } elsif (-e $directory) {
-    print "Cannot change directory to '$directory': it is not a directory\n";
-  } else {
-    print "Chdir to $directory failed: No such file or directory\n";
-  }
-  if($failure==1){
-  $error=1;
-  $exitcode=4;
-  print "Test suite `$tesh_file': NOK (system error)\n";
-  exit 4;
-  }
-}
+BEGIN {
+    if (RUNNING_ON_WINDOWS) { # Missing on windows
+        *WIFEXITED   = sub { not $_[0] & 127 };
+        *WEXITSTATUS = sub { $_[0] >> 8 };
+        *WIFSIGNALED = sub { ( $_[0] & 127 ) && ( $_[0] & 127 != 127 ) };
+        *WTERMSIG    = sub { $_[0] & 127 };
 
-sub setenv_cmd {
-  my($var,$ctn);
-  if ($_[0] =~ /^(.*)=(.*)$/) {
-    ($var,$ctn)=($1,$2);
-  }elsif ($_[1] =~ /^(.*)=(.*)$/) {
-    ($var,$ctn)=($1,$2);
-  } else {
-      die "[Tesh/CRITICAL] Malformed argument to setenv: expected 'name=value' but got '$_[1]'\n";
-  }
-
-  print "[Tesh/INFO] setenv $var=$ctn\n";
-  $environ{$var} = $ctn;
+       # used on the command lines
+       $environ{'EXEEXT'} = ".exe";
+    }
 }
 
-# Main option parsing sub
-
-sub get_options {
-  # remove the tesh file from the ARGV used
-  my @ARGV = @_;
-  $tesh_file = pop @ARGV;
-
-  # temporary arrays for GetOption
-  my @verbose = ();
-  my @cfg;
-  my $log; # ignored
-
 
-  my %opt = (
-    "help"  => 0,
-    "debug"   => 0,
-    "verbose" => 0
-    );
+####
+#### Command line option handling
+####
 
-  Getopt::Long::config('bundling', 'no_getopt_compat', 'no_auto_abbrev');
+my %opts = ( "debug" => 0,
+             "timeout" => 5, # No command should run any longer than 5 seconds by default
+           );
 
-  GetOptions(
-    'help|h'   => \$opt{'help'},
-
-    'verbose|v'  => \@verbose,
-    'debug|d'  => \$opt{"debug"},
+Getopt::Long::config( 'bundling', 'no_getopt_compat', 'no_auto_abbrev' );
+GetOptions(
+    'debug|d' => \$opts{"debug"},
 
     'difftool=s' => \$diff_tool,
 
-    'cd=s'     => \&cd_cmd,
-    'timeout=s'  => \$opt{'timeout'},
-    'setenv=s'   => \&setenv_cmd,
-    'cfg=s'    => \@cfg,
-    'log=s'    => \$log,
-    'enable-coverage+'  => \$enable_coverage,
-    );
+    'cd=s'      => sub { cd_cmd( $_[1] ) },
+    'timeout=s' => \$opts{'timeout'},
+    'setenv=s'  => sub { setenv_cmd( $_[1] ) },
+    'cfg=s' => sub { $opts{'cfg'} .= " --cfg=$_[1]" },
+    'enable-coverage+' => \$enable_coverage,
+);
+
+$tesh_file = pop @ARGV;
+$tesh_name = $tesh_file;
+$tesh_name =~ s|^.*?/([^/]*)$|$1|;
 
-  if($enable_coverage){
-    print "Enable coverage\n";
-  }
+print "Enable coverage\n" if ($enable_coverage);
 
-  if($diff_tool){
+if ($diff_tool) {
     use File::Temp qw/ tempfile /;
-    ($diff_tool_tmp_fh, $diff_tool_tmp_filename) = tempfile();
+    ( $diff_tool_tmp_fh, $diff_tool_tmp_filename ) = tempfile();
     print "New tesh: $diff_tool_tmp_filename\n";
-  }
+}
 
-  unless($tesh_file=~/(.*)\.tesh/){
-    $tesh_file="(stdin)";
-    $tesh_name="(stdin)";
+if ( $tesh_file =~ m/(.*)\.tesh/ ) {
+    print "Test suite `$tesh_file'\n";
+} else {
+    $tesh_name = "(stdin)";
     print "Test suite from stdin\n";
-  }else{
-    $tesh_name=$1;
-    print "Test suite `$tesh_name'\n";
-  }
-
-  $opt{'verbose'} = scalar @verbose;
-  foreach (@cfg) {
-    $opt{'cfg'} .= " --cfg=$_";
-  }
-  return %opt;
 }
 
-my %opts = get_options(@ARGV);
-
-##
-## File parsing
-##
-my($nb_arg)=0;
-my($old_buffer);
-my($linebis);
-my($SIGABRT)=0;
-my($verbose)=0;
-my($return)=-1;
-my($pid);
-my($result);
-my($result_err);
-my($forked);
-my($config)="";
-my($tesh_command)=0;
-my(@buffer_tesh)=();
-
-#eval {
-  use POSIX;
-
-  sub exit_status {
-    my $status = shift;
-    if (POSIX::WIFEXITED($status)) {
-      $exitcode=POSIX::WEXITSTATUS($status)+40;
-      return "returned code ".POSIX::WEXITSTATUS($status);
-    } elsif (POSIX::WIFSIGNALED($status)) {
-      my $code;
-      if (POSIX::WTERMSIG($status) == SIGINT){$code="SIGINT"; }
-      elsif  (POSIX::WTERMSIG($status) == SIGTERM) {$code="SIGTERM"; }
-      elsif  (POSIX::WTERMSIG($status) == SIGKILL) {$code= "SIGKILL"; }
-      elsif  (POSIX::WTERMSIG($status) == SIGABRT) {$code="SIGABRT"; }
-      elsif  (POSIX::WTERMSIG($status) == SIGSEGV) {$code="SIGSEGV" ;}
-      $exitcode=POSIX::WTERMSIG($status)+4;
-      return "got signal $code";
-    }
-    return "Unparsable status. Is the process stopped?";
-  }
-#};
-#if ($@) { # no POSIX available?
-#  warn "POSIX not usable to parse the return value of forked child: $@\n";
-#  sub exit_status {
-#    return "returned code -1 $@ ";
-#  }
-#}
+###########################################################################
 
 sub exec_cmd {
-  my %cmd = %{$_[0]};
-  if ($opts{'debug'}) {
-    print "IN BEGIN\n";
-    map {print "  $_"} @{$cmd{'in'}};
-    print "IN END\n";
-    print "OUT BEGIN\n";
-    map {print "  $_"} @{$cmd{'out'}};
-    print "OUT END\n";
-    print "CMD: $cmd{'cmd'}\n";
-  }
-
-  # cleanup the command line
-  if($OS eq "WIN") {
-      var_subst($cmd{'cmd'}, "EXEEXT", ".exe");
-  } else {
-      var_subst($cmd{'cmd'}, "EXEEXT", "");
-  }
-
-  # substitute environ variables
-  foreach my $key (keys %environ) {
-      $cmd{'cmd'} = var_subst($cmd{'cmd'}, $key, $environ{$key});
-  }
-  # substitute remaining variables, if any
-  while ($cmd{'cmd'} =~ /\${(\w+)(?::[=-][^}]*)?}/) {
-      $cmd{'cmd'} = var_subst($cmd{'cmd'}, $1, "");
-  }
-  while ($cmd{'cmd'} =~ /\$(\w+)/) {
-      $cmd{'cmd'} = var_subst($cmd{'cmd'}, $1, "");
-  }
-
-  # add cfg options
-  $cmd{'cmd'} .= " $opts{'cfg'}" if (defined($opts{'cfg'}) && length($opts{'cfg'}));
-
-  # final cleanup
-  $cmd{'cmd'} =~ s/^\s+//;
-  $cmd{'cmd'} =~ s/\s+$//;
-
-  print "[$tesh_name:$cmd{'line'}] $cmd{'cmd'}\n" ;
-
-  ###
-  # exec the command line
-  ###  $line =~ s/\r//g;
-
-  $cmd{'got'} = IO::File->new_tmpfile;
-  $cmd{'got'}->autoflush(1);
-  local *E = $cmd{'got'};
-  $cmd{'pid'} = open3(\*CHILD_IN,  ">&E",  ">&E",
-                      quotewords('\s+', 0, $cmd{'cmd'}));
-
-  # push all provided input to executing child
-  map { print CHILD_IN "$_\n"; }  @{$cmd{'in'}};
-  close CHILD_IN;
-
-  # if timeout specified, fork and kill executing child at the end of timeout
-  if (defined($cmd{'timeout'}) or defined($opts{'timeout'})){
-    $time_to_wait= defined($cmd{'timeout'}) ? $cmd{'timeout'} : $opts{'timeout'};
-    $forked = fork();
-    $timeout=-1;
-    die "fork() failed: $!" unless defined $forked;
-    if ( $forked == 0 ) { # child
-      sleep $time_to_wait;
-      kill(SIGTERM, $cmd{'pid'});
-      sleep 1;
-      kill(SIGKILL, $cmd{'pid'});
-      exit $time_to_wait;
+    my %cmd = %{ $_[0] };
+    if ( $opts{'debug'} ) {
+        map { print "IN: $_\n" } @{ $cmd{'in'} };
+        map { print "OUT: $_\n" } @{ $cmd{'out'} };
+        print "CMD: $cmd{'cmd'}\n";
     }
-  }
-
-
-  # Cleanup the executing child, and kill the timeouter brother on need
-  $cmd{'return'} = 0 unless defined($cmd{'return'});
-  if($cmd{'background'} != 1){
-    waitpid ($cmd{'pid'}, 0);
-    $cmd{'gotret'} = exit_status($?);
-    parse_out(\%cmd);
-  }else{
-    # & commands, which will be handled at the end
-    push @bg_cmds, \%cmd;
-    # no timeout for background commands
-    if($forked){
-       kill(SIGKILL, $forked);
-       $timeout=0;
-       $forked=0;
+
+    # substitute environment variables
+    foreach my $key ( keys %environ ) {
+        $cmd{'cmd'} = var_subst( $cmd{'cmd'}, $key, $environ{$key} );
     }
-  }
-}
 
+    # substitute remaining variables, if any
+    while ( $cmd{'cmd'} =~ /\${(\w+)(?::[=-][^}]*)?}/ ) {
+        $cmd{'cmd'} = var_subst( $cmd{'cmd'}, $1, "" );
+    }
+    while ( $cmd{'cmd'} =~ /\$(\w+)/ ) {
+        $cmd{'cmd'} = var_subst( $cmd{'cmd'}, $1, "" );
+    }
 
-sub parse_out {
-  my %cmd = %{$_[0]};
-  my $gotret=$cmd{'gotret'};
+    # add cfg options
+    $cmd{'cmd'} .= " $opts{'cfg'}"
+      if ( defined( $opts{'cfg'} ) && length( $opts{'cfg'} ) );
 
-  my $wantret;
+    # finally trim any remaining space chars
+    $cmd{'cmd'} =~ s/^\s+//;
+    $cmd{'cmd'} =~ s/\s+$//;
 
-  if(defined($cmd{'expect'}) and ($cmd{'expect'} ne "")){
-    $wantret = "got signal $cmd{'expect'}";
-  }else{
-    $wantret = "returned code ".(defined($cmd{'return'})? $cmd{'return'} : 0);
-  }
+    print "[$tesh_name:$cmd{'line'}] $cmd{'cmd'}\n";
 
-  local *got = $cmd{'got'};
-  seek(got,0,0);
-  # pop all output from executing child
-  my @got;
-  while(defined(my $got=<got>)) {
-    $got =~ s/\r//g;
-    chomp $got;
-    print $diff_tool_tmp_fh "> $got\n" if ($diff_tool);
+    $cmd{'return'} ||= 0;
+    $cmd{'timeout'} ||= $opts{'timeout'};
+    
 
-    if (!($enable_coverage and $got=~ /^profiling:/)){
-      push @got, $got;
-    }
-  }
+    ###
+    # exec the command line
 
-  if ($cmd{'sort'}){
-    # Save the unsorted observed output to report it on error.
-    map { push @{$cmd{'unsorted got'}}, $_ } @got;
+    my @cmdline = quotewords( '\s+', 0, $cmd{'cmd'} );
+    my $input = defined($cmd{'in'})? join("\n",@{$cmd{'in'}}) : "";
+    my $output = " " x 10240; $output = ""; # Preallocate 10kB, and reset length to 0
+    $cmd{'got'} = \$output;
+    $cmd{'job'} = start \@cmdline, '<', \$input, '>&', \$output, 
+                  ($cmd{'timeout'} eq 'no' ? () : timeout($cmd{'timeout'}));
 
-    sub mysort{
-        substr($a, 0, $sort_prefix) cmp substr($b, 0, $sort_prefix)
-    }
-    use sort 'stable';
-    if ($sort_prefix>0) {
-       @got = sort mysort @got;
+    if ( $cmd{'background'} ) {
+       # Just enqueue the job. It will be dealed with at the end
+        push @bg_cmds, \%cmd;
     } else {
-       @got = sort @got;
-    }      
-    while (@got and $got[0] eq "") {
-      shift @got;
+       # Deal with its ending conditions right away
+        analyze_result( \%cmd );
     }
+}
 
-    # Sort the expected output to make it easier to write for humans
-    if(defined($cmd{'out'})){
-      if ($sort_prefix>0) {
-         @{$cmd{'out'}} = sort mysort @{$cmd{'out'}};
-      } else {
-         @{$cmd{'out'}} = sort @{$cmd{'out'}};
-      }
-      while (@{$cmd{'out'}} and ${$cmd{'out'}}[0] eq "") {
-        shift @{$cmd{'out'}};
-      }
+sub analyze_result {
+    my %cmd    = %{ $_[0] };
+    $cmd{'timeouted'} = 0; # initialization
+
+    # Wait for the end of the child process
+    #####
+    eval {
+       finish( $cmd{'job'} );
+    };
+    if ($@) { # deal with the errors that occured in the child process
+       if ($@ =~ /timeout/) {
+           $cmd{'job'}->kill_kill;
+           $cmd{'timeouted'} = 1;
+       } elsif ($@ =~ /^ack / and $@ =~ /pipe/) { # IPC::Run is not very expressive about the pipes that it gets :(
+           print STDERR "Tesh: Broken pipe (ignored).\n";
+       } else {
+           die $@; # Don't know what it is, so let it go.
+       }
+    } 
+
+    # Gather information
+    ####
+    
+    # pop all output from executing child
+    my @got;
+    map { print "GOT: $_\n" } ${$cmd{'got'}} if $opts{'debug'};
+    foreach my $got ( split("\n", ${$cmd{'got'}}) ) {
+        $got =~ s/\r//g;
+        chomp $got;
+        print $diff_tool_tmp_fh "> $got\n" if ($diff_tool);
+
+        unless ( $enable_coverage and $got =~ /^profiling:/ ) {
+            push @got, $got;
+        }
     }
-  }
-
-  # Did we timeout ? If yes, handle it. If not, kill the forked process.
-
-  if($timeout==-1 and ($gotret eq "got signal SIGTERM" or $gotret eq "got signal SIGKILL")){
-    $gotret="return code 0";
-    $timeout=1;
-    $gotret= "timeout after $time_to_wait sec";
-    $error=1;
-    $exitcode=3;
-    print STDERR "<$cmd{'file'}:$cmd{'line'}> timeouted. Kill the process.\n";
-  }else{
-    $timeout=0;
-  }
-  if($gotret ne $wantret) {
-    $error=1;
-    my $msg = "Test suite `$cmd{'file'}': NOK (<$cmd{'file'}:$cmd{'line'}> $gotret)\n";
-    if ($timeout!=1) {
-        $msg=$msg."Output of <$cmd{'file'}:$cmd{'line'}> so far:\n";
+
+    # How did the child process terminate?
+    my $status = $?;
+    $cmd{'gotret'} = "Unparsable status. Please report this tesh bug.";
+    if ( $cmd{'timeouted'} ) {
+        $cmd{'gotret'} = "timeout after $cmd{'timeout'} sec";
+        $error    = 1;
+        $exitcode = 3;
+    } elsif ( WIFEXITED($status) ) {
+        $exitcode = WEXITSTATUS($status) + 40;
+       $cmd{'gotret'} = "returned code " . WEXITSTATUS($status);
+    } elsif ( WIFSIGNALED($status) ) {
+        my $code;
+        if    ( WTERMSIG($status) == SIGINT )  { $code = "SIGINT"; }
+        elsif ( WTERMSIG($status) == SIGTERM ) { $code = "SIGTERM"; }
+        elsif ( WTERMSIG($status) == SIGKILL ) { $code = "SIGKILL"; }
+        elsif ( WTERMSIG($status) == SIGABRT ) { $code = "SIGABRT"; }
+        elsif ( WTERMSIG($status) == SIGSEGV ) { $code = "SIGSEGV"; }
+        $exitcode = WTERMSIG($status) + 4;
+        $cmd{'gotret'} = "got signal $code";
     }
-    map {$msg .=  "|| $_\n"} @got;
-    if(!@got) {
-        if($timeout==1){
-        print STDERR "<$cmd{'file'}:$cmd{'line'}> No output before timeout\n";
-        }else{
-        $msg .= "||\n";
-        }
+
+    # How was it supposed to terminate?
+    my $wantret;
+    if ( defined( $cmd{'expect'} ) and ( $cmd{'expect'} ne "" ) ) {
+        $wantret = "got signal $cmd{'expect'}";
+    } else {
+        $wantret = "returned code " . ( defined( $cmd{'return'} ) ? $cmd{'return'} : 0 );
     }
-    $timeout = 0;
-    print STDERR "$msg";
-  }
-
-
-  ###
-  # Check the result of execution
-  ###
-  my $diff;
-  if (defined($cmd{'output display'})){
-    print "[Tesh/INFO] Here is the (ignored) command output:\n";
-    map { print "||$_\n" } @got;
-  }
-  elsif (!defined($cmd{'output ignore'})){
-    $diff = build_diff(\@{$cmd{'out'}}, \@got);
-  }else{
-    print "(ignoring the output of <$cmd{'file'}:$cmd{'line'}> as requested)\n"
-  }
-  if (length $diff) {
-    print "Output of <$cmd{'file'}:$cmd{'line'}> mismatch".($cmd{'sort'}?" (even after sorting)":"").":\n";
-    map { print "$_\n" } split(/\n/,$diff);
-    if ($cmd{'sort'}) {
-       print "WARNING: Both the observed output and expected output were sorted as requested.\n";
-       print "WARNING: Output were only sorted using the $sort_prefix first chars.\n"
-         if ($sort_prefix>0);
-       print "WARNING: Use <! output sort 19> to sort by simulated date and process ID only.\n";
-       # print "----8<---------------  Begin of unprocessed observed output (as it should appear in file):\n";
-       # map {print "> $_\n"} @{$cmd{'unsorted got'}};
-       # print "--------------->8----  End of the unprocessed observed output.\n";
+
+    # Enforce the outcome
+    ####
+    
+    # Did it end as expected?
+    if ( $cmd{'gotret'} ne $wantret ) {
+        $error = 1;
+        my $msg = "Test suite `$tesh_name': NOK (<$tesh_name:$cmd{'line'}> $cmd{'gotret'})\n";
+        if ( scalar @got ) {
+            $msg = $msg . "Output of <$tesh_name:$cmd{'line'}> so far:\n";
+           map { $msg .= "|| $_\n" } @got;
+        } else {
+           $msg .= "<$tesh_name:$cmd{'line'}> No output so far.\n";
+       }
+        print STDERR "$msg";
     }
 
-    print "Test suite `$cmd{'file'}': NOK (<$cmd{'file'}:$cmd{'line'}> output mismatch)\n";
-    $error=1;
-    $exitcode=2;
-  }
-}
+    # Does the output match?
+    if ( $cmd{'sort'} ) {
+        sub mysort {
+            substr( $a, 0, $sort_prefix ) cmp substr( $b, 0, $sort_prefix );
+        }
+        use sort 'stable';
+        if ( $sort_prefix > 0 ) {
+            @got = sort mysort @got;
+        } else {
+            @got = sort @got;
+        }
+        while ( @got and $got[0] eq "" ) {
+            shift @got;
+        }
 
-sub mkfile_cmd {
-  my %cmd = %{$_[0]};
-  my $file = $cmd{'arg'};
-  print "[Tesh/INFO] mkfile $file\n";
+        # Sort the expected output too, to make tesh files easier to write for humans
+        if ( defined( $cmd{'out'} ) ) {
+            if ( $sort_prefix > 0 ) {
+                @{ $cmd{'out'} } = sort mysort @{ $cmd{'out'} };
+            } else {
+                @{ $cmd{'out'} } = sort @{ $cmd{'out'} };
+            }
+            while ( @{ $cmd{'out'} } and ${ $cmd{'out'} }[0] eq "" ) {
+                shift @{ $cmd{'out'} };
+            }
+        }
+    }
 
-  unlink($file);
-  open(FILE,">$file") or die "[Tesh/CRITICAL] Unable to create file $file: $!\n";
-  print FILE join("\n", @{$cmd{'in'}});
-  print FILE "\n" if (scalar @{$cmd{'in'}} > 0);
-  close(FILE);
+    # Report the output if asked so or if it differs
+    if ( defined( $cmd{'output display'} ) ) {
+        print "[Tesh/INFO] Here is the (ignored) command output:\n";
+        map { print "||$_\n" } @got;
+    } elsif ( defined( $cmd{'output ignore'} ) ) {
+        print "(ignoring the output of <$tesh_name:$cmd{'line'}> as requested)\n";
+    } else {
+        my $diff = build_diff( \@{ $cmd{'out'} }, \@got );
+    
+       if ( length $diff ) {
+           print "Output of <$tesh_name:$cmd{'line'}> mismatch" . ( $cmd{'sort'} ? " (even after sorting)" : "" ) . ":\n";
+           map { print "$_\n" } split( /\n/, $diff );
+           if ( $cmd{'sort'} ) {
+               print "WARNING: Both the observed output and expected output were sorted as requested.\n";
+               print "WARNING: Output were only sorted using the $sort_prefix first chars.\n"
+                   if ( $sort_prefix > 0 );
+               print "WARNING: Use <! output sort 19> to sort by simulated date and process ID only.\n";
+
+               # print "----8<---------------  Begin of unprocessed observed output (as it should appear in file):\n";
+               # map {print "> $_\n"} @{$cmd{'unsorted got'}};
+               # print "--------------->8----  End of the unprocessed observed output.\n";
+           }
+           
+           print "Test suite `$tesh_name': NOK (<$tesh_name:$cmd{'line'}> output mismatch)\n";
+           exit 2;
+       }
+    }
 }
 
 # parse tesh file
-#my $teshfile=$tesh_file;
-#$teshfile=~ s{\.[^.]+$}{};
-
-unless($tesh_file eq "(stdin)"){
-  open TESH_FILE, $tesh_file or die "[Tesh/CRITICAL] Unable to open $tesh_file $!\n";
+my $infh;    # The file descriptor from which we should read the teshfile
+if ( $tesh_name eq "(stdin)" ) {
+    $infh = *STDIN;
+} else {
+    open $infh, $tesh_file
+      or die "[Tesh/CRITICAL] Unable to open $tesh_file: $!\n";
 }
 
-my %cmd; # everything about the next command to run
-my $line_num=0;
-my $finished =0;
-LINE: while (not $finished and not $error) {
-  my $line;
-
-
-  if ($tesh_file ne "(stdin)" and !defined($line=<TESH_FILE>)){
-    $finished=1;
-    next LINE;
-  }elsif ($tesh_file eq "(stdin)" and !defined($line=<>)){
-    $finished=1;
-    next LINE;
-  }
-
-  $line_num++;
-  chomp $line;
-  $line =~ s/\r//g;
-  print "[TESH/debug] $line_num: $line\n" if $opts{'debug'};
-  my $next;
-  # deal with line continuations
-  while ($line =~ /^(.*?)\\$/) {
-    $next=<TESH_FILE>;
-    die "[TESH/CRITICAL] Continued line at end of file\n"
-      unless defined($next);
+my %cmd;     # everything about the next command to run
+my $line_num = 0;
+LINE: while ( not $error and defined( my $line = <$infh> )) {
+    chomp $line;
+    $line =~ s/\r//g;
+
     $line_num++;
-    chomp $next;
-    print "[TESH/debug] $line_num: $next\n" if $opts{'debug'};
-    $line = $1.$next;
-  }
-
-  # Push delayed commands on empty lines
-  unless ($line =~ m/^(.)(.*)$/) {
-    if (defined($cmd{'cmd'}))  {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    print $diff_tool_tmp_fh "$line\n" if ($diff_tool);
-    next LINE;
-  }
-
-  my ($cmd,$arg) = ($1,$2);
-  print $diff_tool_tmp_fh "$line\n" if ($diff_tool and $cmd ne '>');
-  $arg =~ s/^ //g;
-  $arg =~ s/\r//g;
-  $arg =~ s/\\\\/\\/g;
-  # handle the commands
-  if ($cmd =~ /^#/) {    #comment
-  } elsif ($cmd eq '>'){    #expected result line
-    print "[TESH/debug] push expected result\n" if $opts{'debug'};
-    push @{$cmd{'out'}}, $arg;
-
-  } elsif ($cmd eq '<') {    # provided input
-    print "[TESH/debug] push provided input\n" if $opts{'debug'};
-    push @{$cmd{'in'}}, $arg;
-
-  } elsif ($cmd eq 'p') {    # comment
-    print "[$tesh_name:$line_num] $arg\n";
-
-  } elsif ($cmd eq '$') {  # Command
-    # if we have something buffered, run it now
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    if ($arg =~ /^\s*mkfile /){      # "mkfile" command line
-      die "[TESH/CRITICAL] Output expected from mkfile command!\n" if scalar @{cmd{'out'}};
-
-      $cmd{'arg'} = $arg;
-      $cmd{'arg'} =~ s/\s*mkfile //;
-      mkfile_cmd(\%cmd);
-      %cmd = ();
-
-    } elsif ($arg =~ /^\s*cd /) {
-      die "[TESH/CRITICAL] Input provided to cd command!\n" if scalar @{cmd{'in'}};
-      die "[TESH/CRITICAL] Output expected from cd command!\n" if scalar @{cmd{'out'}};
-
-      $arg =~ s/^ *cd //;
-      cd_cmd("",$arg);
-      %cmd = ();
-
-    } else { # regular command
-      $cmd{'cmd'} = $arg;
-      $cmd{'file'} = $tesh_file;
-      $cmd{'line'} = $line_num;
+    print "[TESH/debug] $line_num: $line\n" if $opts{'debug'};
+
+    # deal with line continuations
+    while ( $line =~ /^(.*?)\\$/ ) {
+        my $next = <$infh>;
+        die "[TESH/CRITICAL] Continued line at end of file\n"
+          unless defined($next);
+        $line_num++;
+        chomp $next;
+        print "[TESH/debug] $line_num: $next\n" if $opts{'debug'};
+        $line = $1 . $next;
     }
-  }
-  elsif($cmd eq '&'){      # parallel command line
 
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    $cmd{'background'} = 1;
-    $cmd{'cmd'} = $arg;
-    $cmd{'file'} = $tesh_file;
-    $cmd{'line'} = $line_num;
-  }
-  elsif($line =~ /^!\s*output sort/){    #output sort
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    $cmd{'sort'} = 1;
-    if ($line =~ /^!\s*output sort\s+(\d+)/) {
-        $sort_prefix = $1;
-    }
-  }
-  elsif($line =~ /^!\s*output ignore/){    #output ignore
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    $cmd{'output ignore'} = 1;
-  }
-  elsif($line =~ /^!\s*output display/){    #output display
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    $cmd{'output display'} = 1;
-  }
-  elsif($line =~ /^!\s*expect signal (\w*)/) {#expect signal SIGABRT
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-print "hey\n";
-    $cmd{'expect'} = "$1";
-  }
-  elsif($line =~ /^!\s*expect return/){    #expect return
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    $line =~ s/^! expect return //g;
-    $line =~ s/\r//g;
-    $cmd{'return'} = $line;
-  }
-  elsif($line =~ /^!\s*setenv/){    #setenv
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    $line =~ s/^! setenv //g;
-    $line =~ s/\r//g;
-    setenv_cmd($line);
-  }
-  elsif($line =~ /^!\s*include/){    #include
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
-    }
-    print color("red"), "[Tesh/CRITICAL] need include";
-    print color("reset"), "\n";
-    die;
-  }
-  elsif($line =~ /^!\s*timeout/){    #timeout
-    if (defined($cmd{'cmd'})) {
-      exec_cmd(\%cmd);
-      %cmd = ();
+    # If the line is empty, run any previously defined block and proceed to next line
+    unless ( $line =~ m/^(.)(.*)$/ ) {
+        if ( defined( $cmd{'cmd'} ) ) {
+            exec_cmd( \%cmd );
+            %cmd = ();
+        }
+        print $diff_tool_tmp_fh "$line\n" if ($diff_tool);
+        next LINE;
     }
-    $line =~ s/^! timeout //;
-    $line =~ s/\r//g;
-    $cmd{'timeout'} = $line;
-  } else {
-    die "[TESH/CRITICAL] parse error: $line\n";
-  }
-  if($forked){
-   kill(SIGKILL, $forked);
-   $timeout=0;
-  }
-
-}
 
+    my ( $cmd, $arg ) = ( $1, $2 );
+    print $diff_tool_tmp_fh "$line\n" if ( $diff_tool and $cmd ne '>' );
+    $arg =~ s/^ //g;
+    $arg =~ s/\r//g;
+    $arg =~ s/\\\\/\\/g;
+
+    # Deal with the lines that can contribute to the current command block
+    if ( $cmd =~ /^#/ ) {    # comment
+       next LINE;
+    } elsif ( $cmd eq '>' ) {    # expected result line
+        print "[TESH/debug] push expected result\n" if $opts{'debug'};
+        push @{ $cmd{'out'} }, $arg;
+       next LINE;
+
+    } elsif ( $cmd eq '<' ) {    # provided input
+        print "[TESH/debug] push provided input\n" if $opts{'debug'};
+        push @{ $cmd{'in'} }, $arg;
+       next LINE;
+
+    } elsif ( $cmd eq 'p' ) {    # comment
+        print "[$tesh_name:$line_num] $arg\n";
+       next LINE;
+
+    } 
+
+    # We dealt with all sort of lines that can contribute to a command block, so we have something else here.
+    # If we have something buffered, run it now and start a new block
+    if ( defined( $cmd{'cmd'} ) ) {
+       exec_cmd( \%cmd );
+       %cmd = ();
+    }
 
+    # Deal with the lines that must be placed before a command block
+    if ( $cmd eq '$' ) {    # Command
+        if ( $arg =~ /^mkfile / ) {    # "mkfile" command line
+            die "[TESH/CRITICAL] Output expected from mkfile command!\n"
+              if scalar @{ cmd { 'out' } };
+
+            $cmd{'arg'} = $arg;
+            $cmd{'arg'} =~ s/mkfile //;
+            mkfile_cmd( \%cmd );
+            %cmd = ();
+
+        } elsif ( $arg =~ /^\s*cd / ) {
+            die "[TESH/CRITICAL] Input provided to cd command!\n"
+              if scalar @{ cmd { 'in' } };
+            die "[TESH/CRITICAL] Output expected from cd command!\n"
+              if scalar @{ cmd { 'out' } };
+
+            $arg =~ s/^ *cd //;
+            cd_cmd($arg);
+            %cmd = ();
+
+        } else {    # regular command
+            $cmd{'cmd'}  = $arg;
+            $cmd{'line'} = $line_num;
+        }
 
-# Deal with last command
-if (defined($cmd{'cmd'})) {
-  exec_cmd(\%cmd);
-  %cmd = ();
+    } elsif ( $cmd eq '&' ) {    # background command line
+       die "[TESH/CRITICAL] mkfile cannot be run in background\n"
+           if ($arg =~ /^mkfile/);
+       die "[TESH/CRITICAL] cd cannot be run in background\n"
+           if ($arg =~ /^cd/);
+       
+        $cmd{'background'} = 1;
+        $cmd{'cmd'}        = $arg;
+        $cmd{'line'}       = $line_num;
+
+    # Deal with the meta-commands
+    } elsif ( $line =~ /^! (.*)/) {
+       $line = $1;
+
+       if ( $line =~ /^output sort/ ) {
+           $cmd{'sort'} = 1;
+           if ( $line =~ /^output sort\s+(\d+)/ ) {
+               $sort_prefix = $1;
+           }
+       } elsif ($line =~ /^output ignore/ ) {
+           $cmd{'output ignore'} = 1;
+       } elsif ( $line =~ /^output display/ ) {
+           $cmd{'output display'} = 1;
+       } elsif ( $line =~ /^expect signal (\w*)/ ) {
+           $cmd{'expect'} = $1;
+       } elsif ( $line =~ /^expect return/ ) {
+           $line =~ s/^expect return //g;
+           $line =~ s/\r//g;
+           $cmd{'return'} = $line;
+       } elsif ( $line =~ /^setenv/ ) {
+           $line =~ s/^setenv //g;
+           $line =~ s/\r//g;
+           setenv_cmd($line);
+       } elsif ( $line =~ /^timeout/ ) {
+           $line =~ s/^timeout //;
+           $line =~ s/\r//g;
+           $cmd{'timeout'} = $line;
+       }
+    } else {
+        die "[TESH/CRITICAL] parse error: $line\n";
+    }
 }
 
+# We are done reading the input file
+close $infh unless ( $tesh_name eq "(stdin)" );
 
-if($forked){
-   kill(SIGKILL, $forked);
-   $timeout=0;
+# Deal with last command, if any
+if ( defined( $cmd{'cmd'} ) ) {
+    exec_cmd( \%cmd );
+    %cmd = ();
 }
 
-foreach(@bg_cmds){
-  my %test=%{$_};
-  waitpid ($test{'pid'}, 0);
-  $test{'gotret'} = exit_status($?);
-  parse_out(\%test);
+foreach (@bg_cmds) {
+    my %test = %{$_};
+    analyze_result( \%test );
 }
 
-@bg_cmds=();
-
 if ($diff_tool) {
-  close $diff_tool_tmp_fh;
-  system("$diff_tool $diff_tool_tmp_filename $tesh_file");
-  unlink $diff_tool_tmp_filename;
+    close $diff_tool_tmp_fh;
+    system("$diff_tool $diff_tool_tmp_filename $tesh_file");
+    unlink $diff_tool_tmp_filename;
 }
 
-if($error !=0){
+if ( $error != 0 ) {
     exit $exitcode;
-}elsif($tesh_file eq "(stdin)"){
+} elsif ( $tesh_name eq "(stdin)" ) {
     print "Test suite from stdin OK\n";
-}else{
+} else {
     print "Test suite `$tesh_name' OK\n";
 }
 
-#my (@a,@b);
-#push @a,"bl1";   push @b,"bl1";
-#push @a,"bl2";   push @b,"bl2";
-#push @a,"bl3";   push @b,"bl3";
-#push @a,"bl4";   push @b,"bl4";
-#push @a,"bl5";   push @b,"bl5";
-#push @a,"bl6";   push @b,"bl6";
-#push @a,"bl7";   push @b,"bl7";
-##push @a,"Perl";  push @b,"ruby";
-#push @a,"END1";   push @b,"END1";
-#push @a,"END2";   push @b,"END2";
-#push @a,"END3";   push @b,"END3";
-#push @a,"END4";   push @b,"END4";
-#push @a,"END5";   push @b,"END5";
-#push @a,"END6";   push @b,"END6";
-#push @a,"END7";   push @b,"END7";
-#print "Identical:\n". build_diff(\@a,\@b);
-
-#@a = (); @b =();
-#push @a,"AZE"; push @b,"EZA";
-#print "Different:\n".build_diff(\@a,\@b);
-
-use lib "@CMAKE_BINARY_DIR@/bin" ;
-
-use Diff qw(diff); # postpone a bit to have time to change INC
+exit 0;
+
+####
+#### Helper functions
+####
 
 sub build_diff {
-  my $res;
-  my $diff = Diff->new(@_);
-
-  $diff->Base( 1 );   # Return line numbers, not indices
-  my $chunk_count = $diff->Next(-1); # Compute the amount of chuncks
-  return ""   if ($chunk_count == 1 && $diff->Same());
-  $diff->Reset();
-  while(  $diff->Next()  ) {
-    my @same = $diff->Same();
-    if ($diff->Same() ) {
-      if ($diff->Next(0) > 1) { # not first chunk: print 2 first lines
-        $res .= '  '.$same[0]."\n" ;
-        $res .= '  '.$same[1]."\n" if (scalar @same>1);
-      }
-      $res .= "...\n"  if (scalar @same>2);
-#    $res .= $diff->Next(0)."/$chunk_count\n";
-      if ($diff->Next(0) < $chunk_count) { # not last chunk: print 2 last lines
-        $res .= '  '.$same[scalar @same -2]."\n" if (scalar @same>1);
-        $res .= '  '.$same[scalar @same -1]."\n";
-      }
+    my $res;
+    my $diff = Diff->new(@_);
+
+    $diff->Base(1);    # Return line numbers, not indices
+    my $chunk_count = $diff->Next(-1);    # Compute the amount of chuncks
+    return "" if ( $chunk_count == 1 && $diff->Same() );
+    $diff->Reset();
+    while ( $diff->Next() ) {
+        my @same = $diff->Same();
+        if ( $diff->Same() ) {
+            if ( $diff->Next(0) > 1 ) {    # not first chunk: print 2 first lines
+                $res .= '  ' . $same[0] . "\n";
+                $res .= '  ' . $same[1] . "\n" if ( scalar @same > 1 );
+            }
+            $res .= "...\n" if ( scalar @same > 2 );
+
+            #    $res .= $diff->Next(0)."/$chunk_count\n";
+            if ( $diff->Next(0) < $chunk_count ) {    # not last chunk: print 2 last lines
+                $res .= '  ' . $same[ scalar @same - 2 ] . "\n"
+                  if ( scalar @same > 1 );
+                $res .= '  ' . $same[ scalar @same - 1 ] . "\n";
+            }
+        }
+        next if $diff->Same();
+        map { $res .= "- $_\n" } $diff->Items(1);
+        map { $res .= "+ $_\n" } $diff->Items(2);
     }
-    next if  $diff->Same();
-    map { $res .= "- $_\n" } $diff->Items(1);
-    map { $res .= "+ $_\n" } $diff->Items(2);
-  }
-  return $res;
+    return $res;
 }
 
+# Helper function replacing any occurence of variable '$name' by its '$value'
+# As in Bash, ${$value:=BLABLA} is rewritten to $value if set or to BLABLA if $value is not set
+sub var_subst {
+    my ( $text, $name, $value ) = @_;
+    if ($value) {
+        $text =~ s/\${$name(?::[=-][^}]*)?}/$value/g;
+        $text =~ s/\$$name(\W|$)/$value$1/g;
+    } else {
+        $text =~ s/\${$name:=([^}]*)}/$1/g;
+        $text =~ s/\${$name}//g;
+        $text =~ s/\$$name(\W|$)/$1/g;
+    }
+    return $text;
+}
+
+################################  The possible commands  ################################
+
+sub mkfile_cmd($) {
+    my %cmd  = %{ $_[0] };
+    my $file = $cmd{'arg'};
+    print STDERR "[Tesh/INFO] mkfile $file. Ctn: >>".join( '\n', @{ $cmd{'in'} })."<<\n"
+      if $opts{'debug'};
 
+    unlink($file);
+    open( FILE, ">$file" )
+      or die "[Tesh/CRITICAL] Unable to create file $file: $!\n";
+    print FILE join( "\n", @{ $cmd{'in'} } );
+    print FILE "\n" if ( scalar @{ $cmd{'in'} } > 0 );
+    close(FILE);
+}
+
+# Command CD. Just change to the provided directory
+sub cd_cmd($) {
+    my $directory = shift;
+    my $failure   = 1;
+    if ( -e $directory && -d $directory ) {
+        chdir("$directory");
+        print "[Tesh/INFO] change directory to $directory\n";
+        $failure = 0;
+    } elsif ( -e $directory ) {
+        print "Cannot change directory to '$directory': it is not a directory\n";
+    } else {
+        print "Chdir to $directory failed: No such file or directory\n";
+    }
+    if ( $failure == 1 ) {
+        print "Test suite `$tesh_name': NOK (system error)\n";
+        exit 4;
+    }
+}
+
+# Command setenv. Gets "variable=content", and update the environment accordingly
+sub setenv_cmd($) {
+    my $arg = shift;
+    if ( $arg =~ /^(.*)=(.*)$/ ) {
+        my ( $var, $ctn ) = ( $1, $2 );
+        print "[Tesh/INFO] setenv $var=$ctn\n";
+        $environ{$var} = $ctn;
+       $ENV{$var} = $ctn;
+    } else {
+        die "[Tesh/CRITICAL] Malformed argument to setenv: expected 'name=value' but got '$arg'\n";
+    }
+}