00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 #ifndef COMPONENTS_TRIG_CPU_BARRIER_TREE_TRIGGERED_H
00014 #define COMPONENTS_TRIG_CPU_BARRIER_TREE_TRIGGERED_H
00015
00016 #include "sst/elements/portals4_sm/trig_cpu/application.h"
00017 #include "sst/elements/portals4_sm/trig_cpu/trig_cpu.h"
00018 #include "sst/elements/portals4_sm/trig_cpu/portals.h"
00019
00020 class barrier_tree_triggered : public application {
00021 public:
00022 barrier_tree_triggered(trig_cpu *cpu) : application(cpu), init(false), algo_count(0)
00023 {
00024 radix = cpu->getRadix();
00025 ptl = cpu->getPortalsHandle();
00026
00027
00028 boost::tie(my_root, my_children) = buildBinomialTree(radix);
00029 num_children = my_children.size();
00030 }
00031
00032 bool
00033 operator()(Event *ev)
00034 {
00035 ptl_md_t md;
00036 ptl_me_t me;
00037
00038 crBegin();
00039
00040 if (!init) {
00041
00042 ptl->PtlCTAlloc(PTL_CT_OPERATION, up_tree_ct_h);
00043 me.start = NULL;
00044 me.length = 0;
00045 me.match_bits = 0;
00046 me.ignore_bits = 0;
00047 me.ct_handle = up_tree_ct_h;
00048 ptl->PtlMEAppend(PT_UP, me, PTL_PRIORITY_LIST, NULL, up_tree_me_h);
00049
00050 ptl->PtlCTAlloc(PTL_CT_OPERATION, down_tree_ct_h);
00051 me.start = NULL;
00052 me.length = 0;
00053 me.match_bits = 0;
00054 me.ignore_bits = 0;
00055 me.ct_handle = down_tree_ct_h;
00056 ptl->PtlMEAppend(PT_DOWN, me, PTL_PRIORITY_LIST, NULL, down_tree_me_h);
00057
00058 md.start = NULL;
00059 md.length = 0;
00060 md.eq_handle = PTL_EQ_NONE;
00061 md.ct_handle = PTL_CT_NONE;
00062 ptl->PtlMDBind(md, &my_md_h);
00063
00064 init = true;
00065 crReturn();
00066 start_noise_section();
00067 }
00068
00069
00070 start_time = cpu->getCurrentSimTimeNano();
00071 cpu->addBusyTime("200ns");
00072 crReturn();
00073
00074 algo_count++;
00075
00076 ptl->PtlEnableCoalesce();
00077 crReturn();
00078
00079 if (num_children == 0) {
00080 ptl->PtlPut(my_md_h, 0, 0, 0, my_root, PT_UP, 0, 0, NULL, 0);
00081 crReturn();
00082 } else {
00083 if (my_id != my_root) {
00084 ptl->PtlTriggeredPut(my_md_h, 0, 0, 0, my_root, PT_UP, 0, 0, NULL, 0,
00085 up_tree_ct_h, algo_count * num_children);
00086 crReturn();
00087 } else {
00088 ptl->PtlTriggeredCTInc(down_tree_ct_h, 1, up_tree_ct_h, algo_count * num_children);
00089 crReturn();
00090 }
00091
00092 for (i = 0 ; i < num_children ; ++i) {
00093 ptl->PtlTriggeredPut(my_md_h, 0, 0, 0, my_children[i], PT_DOWN,
00094 0, 0, NULL, 0, down_tree_ct_h, algo_count);
00095 crReturn();
00096 }
00097 }
00098
00099 ptl->PtlDisableCoalesce();
00100 crReturn();
00101
00102 while (!ptl->PtlCTWait(down_tree_ct_h, algo_count)) { crReturn(); }
00103 crReturn();
00104
00105 trig_cpu::addTimeToStats(cpu->getCurrentSimTimeNano()-start_time);
00106
00107 crFinish();
00108 return true;
00109 }
00110
00111 private:
00112 barrier_tree_triggered();
00113 barrier_tree_triggered(const application& a);
00114 void operator=(barrier_tree_triggered const&);
00115
00116 portals *ptl;
00117
00118 SimTime_t start_time;
00119 int radix;
00120 bool init;
00121
00122 ptl_handle_ct_t up_tree_ct_h;
00123 ptl_handle_me_t up_tree_me_h;
00124
00125 ptl_handle_ct_t down_tree_ct_h;
00126 ptl_handle_me_t down_tree_me_h;
00127
00128 ptl_handle_md_t my_md_h;
00129
00130 int i;
00131 int my_root;
00132 std::vector<int> my_children;
00133 int num_children;
00134
00135 static const int PT_UP = 0;
00136 static const int PT_DOWN = 1;
00137
00138 uint64_t algo_count;
00139 };
00140
00141 #endif // COMPONENTS_TRIG_CPU_BARRIER_TREE_TRIGGERED_H