Tweaks, pass by ref.
This commit is contained in:
@@ -8,6 +8,6 @@ run: placer
|
|||||||
clean:
|
clean:
|
||||||
$(RM) *.o placer
|
$(RM) *.o placer
|
||||||
|
|
||||||
placer:placer.o
|
placer: placer.o
|
||||||
|
|
||||||
.PHONY: all run clean
|
.PHONY: all run clean
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
#include <cassert>
|
#include <cassert>
|
||||||
#include <cstddef>
|
#include <cstddef>
|
||||||
@@ -58,7 +59,7 @@ class Container {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// Raw reference to data, meaning T*, only for cleaness of intentions.
|
// Raw reference to data, meaning T*, invented only for cleaness of intentions.
|
||||||
template <class T>
|
template <class T>
|
||||||
class RawRef {
|
class RawRef {
|
||||||
private:
|
private:
|
||||||
@@ -69,8 +70,7 @@ class RawRef {
|
|||||||
void set(const T& value) { *ptr_ = value; }
|
void set(const T& value) { *ptr_ = value; }
|
||||||
};
|
};
|
||||||
|
|
||||||
// Object reference, adds reference counting in container. In real implementation
|
// Object reference, adds reference counting in container.
|
||||||
// we may want to differentiate between
|
|
||||||
template <class T>
|
template <class T>
|
||||||
class ObjRef {
|
class ObjRef {
|
||||||
private:
|
private:
|
||||||
@@ -107,6 +107,12 @@ class ObjRef {
|
|||||||
return *reinterpret_cast<Container**>(ptr_);
|
return *reinterpret_cast<Container**>(ptr_);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename M, int offset>
|
||||||
|
RawRef<M> at() const {
|
||||||
|
return RawRef<M>(
|
||||||
|
reinterpret_cast<M*>(reinterpret_cast<uint8_t*>(ref()) + offset));
|
||||||
|
}
|
||||||
|
|
||||||
void Assign(const ObjRef<T>& other) {
|
void Assign(const ObjRef<T>& other) {
|
||||||
// TODO: optimize for an important case where containers match.
|
// TODO: optimize for an important case where containers match.
|
||||||
if (ptr_) {
|
if (ptr_) {
|
||||||
@@ -118,10 +124,11 @@ class ObjRef {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename M, int offset>
|
ObjRef<T> Clone(Container* container) {
|
||||||
RawRef<M> at() const {
|
ObjRef<T> result = Alloc(container);
|
||||||
return RawRef<M>(
|
// TODO: take into account object references in T!
|
||||||
reinterpret_cast<M*>(reinterpret_cast<uint8_t*>(ref()) + offset));
|
memcpy(result.ref(), ref(), sizeof(T));
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool null() const { return ptr_ == nullptr; }
|
bool null() const { return ptr_ == nullptr; }
|
||||||
@@ -136,8 +143,17 @@ struct List {
|
|||||||
int data_;
|
int data_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
void UpdateElement(ObjRef<List> element) {
|
||||||
|
element.at<int, offsetof(struct List, data_)>().set
|
||||||
|
(element.at<int, offsetof(struct List, data_)>().get() + 10);
|
||||||
|
}
|
||||||
|
|
||||||
|
void DoNotUpdateElement(ObjRef<List> element) {
|
||||||
|
element.at<int, offsetof(struct List, data_)>().set
|
||||||
|
(element.at<int, offsetof(struct List, data_)>().get() + 100);
|
||||||
|
}
|
||||||
|
|
||||||
void test_placer() {
|
void test_placer() {
|
||||||
printf("Start placement\n");
|
|
||||||
Container heap(1024);
|
Container heap(1024);
|
||||||
constexpr int next_offset = offsetof(struct List, next_);
|
constexpr int next_offset = offsetof(struct List, next_);
|
||||||
constexpr int data_offset = offsetof(struct List, data_);
|
constexpr int data_offset = offsetof(struct List, data_);
|
||||||
@@ -151,6 +167,18 @@ void test_placer() {
|
|||||||
cur.at<int, data_offset>().set(i + 2);
|
cur.at<int, data_offset>().set(i + 2);
|
||||||
}
|
}
|
||||||
cur = head;
|
cur = head;
|
||||||
|
// Pass by reference.
|
||||||
|
while (!cur.null()) {
|
||||||
|
UpdateElement(cur);
|
||||||
|
cur = cur.at<ObjRef<List>, next_offset>().get();
|
||||||
|
}
|
||||||
|
// Pass by value.
|
||||||
|
while (!cur.null()) {
|
||||||
|
// We could place clone on stack as well.
|
||||||
|
DoNotUpdateElement(cur.Clone(&heap));
|
||||||
|
cur = cur.at<ObjRef<List>, next_offset>().get();
|
||||||
|
}
|
||||||
|
cur = head;
|
||||||
while (!cur.null()) {
|
while (!cur.null()) {
|
||||||
printf("next is %d\n", cur.at<int, data_offset>().get());
|
printf("next is %d\n", cur.at<int, data_offset>().get());
|
||||||
cur = cur.at<ObjRef<List>, next_offset>().get();
|
cur = cur.at<ObjRef<List>, next_offset>().get();
|
||||||
|
|||||||
Reference in New Issue
Block a user