Commit df5bad60 authored by Antoine Kaufmann's avatar Antoine Kaufmann
Browse files

lib/nicbm: add multi nic runner

This allows multiple behavioral nic models to run on one OS thread
using boost fibers (user-level threads)
parent a6d83b3a
/*
* Copyright 2021 Max Planck Institute for Software Systems, and
* National University of Singapore
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#include "lib/simbricks/nicbm/multinic.h"
#include <string.h>
#include <thread>
#include <vector>
#include <boost/bind.hpp>
#include <boost/fiber/all.hpp>
namespace nicbm {
void MultiNicRunner::CompRunner::YieldPoll() {
boost::this_fiber::yield();
}
int MultiNicRunner::CompRunner::NicIfInit(
struct SimbricksNicIfParams &nsparams) {
volatile bool ready = false;
volatile int result = 0;
// NicIfInit will block, so run it in a separate thread and then wait for it
std::thread t([this, &ready, &nsparams, &result](){
result = Runner::NicIfInit(nsparams);
ready = true;
});
while (!ready)
YieldPoll();
t.join();
return result;
}
MultiNicRunner::CompRunner::CompRunner(Device &dev) : Runner(dev) {
}
MultiNicRunner::MultiNicRunner(DeviceFactory &factory) : factory_(factory) {
}
int MultiNicRunner::RunMain(int argc, char *argv[]) {
int start = 0;
std::vector<Runner *> runners;
std::vector<boost::fibers::fiber *> fibers;
do {
int end;
for (end = start + 1; end < argc && strcmp(argv[end], "--"); end++);
argv[start] = argv[0];
CompRunner *r = new CompRunner(factory_.create());
auto *f = new boost::fibers::fiber(
boost::bind(&CompRunner::RunMain, boost::ref(*r),
end - start, argv + start));
runners.push_back(r);
fibers.push_back(f);
start = end;
} while (start < argc);
for (auto f: fibers) {
f->join();
delete(f);
}
return 0;
}
} // namespace nicbm
/*
* Copyright 2021 Max Planck Institute for Software Systems, and
* National University of Singapore
*
* Permission is hereby granted, free of charge, to any person obtaining
* a copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#ifndef SIMBRICKS_NICBM_MULTINIC_H_
#define SIMBRICKS_NICBM_MULTINIC_H_
#include "lib/simbricks/nicbm/nicbm.h"
namespace nicbm {
class MultiNicRunner {
public:
class DeviceFactory {
public:
virtual Runner::Device &create() = 0;
};
protected:
class CompRunner : public Runner {
protected:
virtual void YieldPoll() override;
virtual int NicIfInit(struct SimbricksNicIfParams &nsparams) override;
public:
explicit CompRunner(Device &dev_);
};
DeviceFactory &factory_;
public:
explicit MultiNicRunner(DeviceFactory &factory);
/** Run the simulation */
int RunMain(int argc, char *argv[]);
};
} // namespace nicbm
#endif // SIMBRICKS_NICBM_MULTINIC_H_
......@@ -24,7 +24,7 @@ include mk/subdir_pre.mk
lib_nicbm := $(d)libnicbm.a
OBJS := $(addprefix $(d),nicbm.o)
OBJS := $(addprefix $(d),nicbm.o multinic.o)
$(lib_nicbm): $(OBJS)
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment