Merge with upstream

metadata
Edgar Velazquez-Armendariz 2013-01-28 01:57:58 -05:00
commit d49e89fb94
21 changed files with 94 additions and 37 deletions

View File

@ -1,5 +1,6 @@
#!/bin/bash
cp /opt/intel/composer_xe_*/compiler/lib/libiomp5.dylib Mitsuba.app/Contents/Frameworks
install_name_tool -id @rpath/libiomp5.dylib Mitsuba.app/Contents/Frameworks/libiomp5.dylib
find Mitsuba.app/Contents/MacOS/ Mitsuba.app/plugins -type f | xargs -n 1 install_name_tool -change libiomp5.dylib @rpath/libiomp5.dylib
find Mitsuba.app/Contents/Frameworks/libmitsuba-* -type f | xargs -n 1 install_name_tool -change libiomp5.dylib @rpath/libiomp5.dylib
find Mitsuba.app/python -type f | xargs -n 1 install_name_tool -change libiomp5.dylib @rpath/libiomp5.dylib

View File

@ -472,7 +472,7 @@ public:
template <typename T> void readArray(T *array, size_t count);
/**
* \brief Read a known-size array from the stream (uses partial template
* \brief Read a known-size array from the stream (uses partial template
* specialization to select a method appropriate to the data type)
*/
template <typename T, size_t N> inline void readArray(T (&arr)[N]) {
@ -484,9 +484,9 @@ public:
* specialization to select a method appropriate to the data type)
*/
template <typename T> void writeArray(const T *array, size_t count);
/**
* \brief Write a known-size array to the stream (uses partial template
* \brief Write a known-size array to the stream (uses partial template
* specialization to select a method appropriate to the data type)
*/
template <typename T, size_t N> inline void writeArray(const T (&arr)[N]) {

View File

@ -141,7 +141,8 @@ protected:
}
inline static void destruct(void *data) {
delete static_cast<ValueType *>(data);
if (data)
delete static_cast<ValueType *>(data);
}
protected:
detail::ThreadLocalBase m_base;

View File

@ -189,6 +189,13 @@ template <typename T> inline TVector1<T> normalize(const TVector1<T> &v) {
return v / v.length();
}
template <typename T> inline TVector1<T> normalizeStrict(const TVector1<T> &v, const char *errMsg) {
Float length = v.length();
if (length == 0)
SLog(EError, "normalizeStrict(): %s", errMsg);
return v / length;
}
template <> inline TVector1<int> TVector1<int>::operator/(int s) const {
#ifdef MTS_DEBUG
if (s == 0)
@ -380,6 +387,13 @@ template <typename T> inline TVector2<T> normalize(const TVector2<T> &v) {
return v / v.length();
}
template <typename T> inline TVector2<T> normalizeStrict(const TVector2<T> &v, const char *errMsg) {
Float length = v.length();
if (length == 0)
SLog(EError, "normalizeStrict(): %s", errMsg);
return v / length;
}
template <> inline TVector2<int> TVector2<int>::operator/(int s) const {
#ifdef MTS_DEBUG
if (s == 0)
@ -582,6 +596,13 @@ template <typename T> inline TVector3<T> normalize(const TVector3<T> &v) {
return v / v.length();
}
template <typename T> inline TVector3<T> normalizeStrict(const TVector3<T> &v, const char *errMsg) {
Float length = v.length();
if (length == 0)
SLog(EError, "normalizeStrict(): %s", errMsg);
return v / length;
}
template <> inline TVector3<int> TVector3<int>::operator/(int s) const {
#ifdef MTS_DEBUG
if (s == 0)
@ -781,6 +802,13 @@ template <typename T> inline TVector4<T> normalize(const TVector4<T> &v) {
return v / v.length();
}
template <typename T> inline TVector4<T> normalizeStrict(const TVector4<T> &v, const char *errMsg) {
Float length = v.length();
if (length == 0)
SLog(EError, "normalizeStrict(): %s", errMsg);
return v / length;
}
template <> inline TVector4<int> TVector4<int>::operator/(int s) const {
#ifdef MTS_DEBUG
if (s == 0)

View File

@ -101,6 +101,9 @@ public:
/// Free the memory taken up by staticInitialization()
static void staticShutdown();
/// Push a cleanup handler to be executed after loading the scene is done
static void pushCleanupHandler(void (*cleanup)());
// -----------------------------------------------------------------------
// Implementation of the SAX DocumentHandler interface
// -----------------------------------------------------------------------

View File

@ -312,9 +312,10 @@ protected:
/**
* \brief Reads the header information of a compressed file, returning
* the version ID. This function assumes the stream is at the beginning
* of the compressed file and leaves the stream located right after the
* header.
* the version ID.
*
* This function assumes the stream is at the beginning of the compressed
* file and leaves the stream located right after the header.
*/
static short readHeader(Stream *stream);

View File

@ -318,11 +318,11 @@ public:
Point2 sample(_sample);
if (sampleSpecular && sampleNested) {
if (sample.x > probSpecular) {
if (sample.x < probSpecular) {
sample.x /= probSpecular;
} else {
sample.x = (sample.x - probSpecular) / (1 - probSpecular);
choseSpecular = false;
} else {
sample.x /= probSpecular;
}
}

View File

@ -321,7 +321,7 @@ public:
(1-Fi) * (1-m_specularSamplingWeight));
/* Importance sample wrt. the Fresnel reflectance */
if (sample.x <= probSpecular) {
if (sample.x < probSpecular) {
bRec.sampledComponent = 0;
bRec.sampledType = EDeltaReflection;
bRec.wo = reflect(bRec.wi);
@ -384,7 +384,7 @@ public:
(1-Fi) * (1-m_specularSamplingWeight));
/* Importance sample wrt. the Fresnel reflectance */
if (sample.x <= probSpecular) {
if (sample.x < probSpecular) {
bRec.sampledComponent = 0;
bRec.sampledType = EDeltaReflection;
bRec.wo = reflect(bRec.wi);

View File

@ -391,7 +391,7 @@ public:
(probSpecular*m_specularSamplingWeight +
(1-probSpecular) * (1-m_specularSamplingWeight));
if (sample.y <= probSpecular) {
if (sample.y < probSpecular) {
sample.y /= probSpecular;
} else {
sample.y = (sample.y - probSpecular) / (1 - probSpecular);

View File

@ -254,7 +254,7 @@ public:
if (child->getClass()->derivesFrom(MTS_CLASS(Texture))) {
if (name == "reflectance" || name == "diffuseReflectance")
m_reflectance = static_cast<Texture *>(child);
if (name == "alpha")
else if (name == "alpha")
m_alpha = static_cast<Texture *>(child);
else
BSDF::addChild(name, child);

View File

@ -447,7 +447,7 @@ public:
(probSpecular*m_specularSamplingWeight +
(1-probSpecular) * (1-m_specularSamplingWeight));
if (sample.y <= probSpecular) {
if (sample.y < probSpecular) {
sample.y /= probSpecular;
} else {
sample.y = (sample.y - probSpecular) / (1 - probSpecular);

View File

@ -50,7 +50,7 @@ void PSSMLTSampler::serialize(Stream *stream, InstanceManager *manager) const {
}
void PSSMLTSampler::configure() {
m_logRatio = -std::log(m_s2/m_s1);
m_logRatio = -math::fastlog(m_s2/m_s1);
m_time = 0;
m_largeStepTime = 0;
m_largeStep = false;

View File

@ -133,22 +133,24 @@ struct ThreadLocalBase::ThreadLocalPrivate {
/// Look up a TLS entry. The goal is to make this operation very fast!
std::pair<void *, bool> get() {
bool existed = true;
void *data;
#if defined(__OSX__)
PerThreadData *ptd = (PerThreadData *) pthread_getspecific(ptdLocal);
#else
PerThreadData *ptd = ptdLocal;
#endif
if(EXPECT_NOT_TAKEN(!ptd)) {
throw std::runtime_error("null per-thread data");
}
if (EXPECT_NOT_TAKEN(!ptd))
throw std::runtime_error("Internal error: call to ThreadLocalPrivate::get() "
" precedes the construction of thread-specific data structures!");
void *data;
/* This is an uncontended thread-local lock (i.e. not to worry) */
boost::lock_guard<boost::recursive_mutex> guard(ptd->mutex);
PerThreadData::key_iterator it = ptd->map.find(this);
if (EXPECT_TAKEN(it != ptd->map.end())) {
data = it->second.data;
} else {
/* This is the first access from this thread */
TLSEntry entry;
entry.data = data = constructFunctor();
entry.destructFunctor = destructFunctor;

View File

@ -189,8 +189,8 @@ Transform Transform::glOrthographic(Float clipLeft, Float clipRight,
}
Transform Transform::lookAt(const Point &p, const Point &t, const Vector &up) {
Vector dir = normalize(t-p);
Vector left = normalize(cross(up, dir));
Vector dir = normalizeStrict(t-p, "lookAt(): 'origin' and 'target' coincide!");
Vector left = normalizeStrict(cross(up, dir), "lookAt(): the forward and upward direction must be linearly independent!");
Vector newUp = cross(dir, left);
Matrix4x4 result, inverse;

View File

@ -137,7 +137,7 @@ Point2 Warp::squareToStdNormal(const Point2 &sample) {
}
Float Warp::squareToStdNormalPdf(const Point2 &pos) {
return INV_TWOPI * std::exp(-(pos.x*pos.x + pos.y*pos.y)/2.0f);
return INV_TWOPI * math::fastexp(-(pos.x*pos.x + pos.y*pos.y)/2.0f);
}
static Float intervalToTent(Float sample) {

View File

@ -31,6 +31,7 @@
#include <mitsuba/core/fresolver.h>
#include <mitsuba/render/scene.h>
#include <boost/algorithm/string.hpp>
#include <boost/unordered_set.hpp>
MTS_NAMESPACE_BEGIN
XERCES_CPP_NAMESPACE_USE
@ -46,6 +47,10 @@ XERCES_CPP_NAMESPACE_USE
level, NULL, __FILE__, __LINE__, fmt, ## __VA_ARGS__)
#endif
typedef void (*CleanupFun) ();
typedef boost::unordered_set<CleanupFun> CleanupSet;
static PrimitiveThreadLocal<CleanupSet> __cleanup_tls;
SceneHandler::SceneHandler(const SAXParser *parser,
const ParameterMap &params, NamedObjectMap *namedObjects,
bool isIncludedFile) : m_parser(parser), m_params(params),
@ -155,6 +160,13 @@ void SceneHandler::startDocument() {
void SceneHandler::endDocument() {
SAssert(m_scene != NULL);
/* Call cleanup handlers */
CleanupSet &cleanup = __cleanup_tls.get();
for (CleanupSet::iterator it = cleanup.begin();
it != cleanup.end(); ++it)
(*it)();
cleanup.clear();
}
void SceneHandler::characters(const XMLCh* const name,
@ -247,6 +259,10 @@ void SceneHandler::startElement(const XMLCh* const xmlName,
m_context.push(context);
}
void SceneHandler::pushCleanupHandler(void (*cleanup)()) {
__cleanup_tls.get().insert(cleanup);
}
void SceneHandler::endElement(const XMLCh* const xmlName) {
std::string name = transcode(xmlName);
ParseContext &context = m_context.top();

View File

@ -260,6 +260,7 @@ void PerspectiveCamera::configure() {
SLog(EError, "Could not parse the focal length (must be of the form "
"<x>mm, where <x> is a positive integer)!");
m_properties.removeProperty("focalLength");
setDiagonalFov(2 * 180/M_PI* std::atan(std::sqrt((Float) (36*36+24*24)) / (2*value)));
}
}

View File

@ -176,7 +176,7 @@ void TriMesh::loadCompressed(Stream *_stream, int index) {
if (stream->getByteOrder() != Stream::ELittleEndian)
Log(EError, "Tried to unserialize a shape from a stream, "
"which was not previously set to little endian byte order!");
"which was not previously set to little endian byte order!");
const short version = readHeader(stream);
@ -305,7 +305,7 @@ int TriMesh::readOffsetDictionary(Stream *stream, short version,
+ sizeof(char) // Name
+ 2*sizeof(uint64_t) // Number of vertices and triangles
+ 3*sizeof(float) // One vertex
+ 3*sizeof(uint32_t)); // One triange
+ 3*sizeof(uint32_t)); // One triangle
if (streamSize >= minSize) {
outOffsets.resize(count);
@ -314,9 +314,8 @@ int TriMesh::readOffsetDictionary(Stream *stream, short version,
if (typeid(size_t) == typeid(uint64_t)) {
stream->readArray(&outOffsets[0], count);
} else {
for (size_t i = 0; i < count; ++i) {
outOffsets[i] = static_cast<size_t>(stream->readSize());
}
for (size_t i = 0; i < count; ++i)
outOffsets[i] = stream->readSize();
}
} else {
stream->seek(stream->getSize() - sizeof(uint32_t) * (count + 1));
@ -325,7 +324,7 @@ int TriMesh::readOffsetDictionary(Stream *stream, short version,
stream->readArray(&outOffsets[0], count);
} else {
for (size_t i = 0; i < count; ++i) {
outOffsets[i] = stream->readUInt();
outOffsets[i] = (size_t) stream->readUInt();
}
}
}

View File

@ -52,8 +52,8 @@ public:
Float eval(Float x) const {
Float alpha = -1.0f / (2.0f * m_stddev*m_stddev);
return std::max((Float) 0.0f,
std::exp(alpha * x * x) -
std::exp(alpha * m_radius * m_radius));
math::fastexp(alpha * x * x) -
math::fastexp(alpha * m_radius * m_radius));
}
std::string toString() const {

View File

@ -17,6 +17,7 @@
*/
#include <mitsuba/render/trimesh.h>
#include <mitsuba/render/scenehandler.h>
#include <mitsuba/core/properties.h>
#include <mitsuba/core/fstream.h>
#include <mitsuba/core/fresolver.h>
@ -211,16 +212,15 @@ public:
private:
/**
* Helper class for loading serialized meshes from the same file
* Helper class for loading serialized meshes from the same file
* repeatedly: it is common for scene to load multiple meshes from the same
* file, most times even in ascending order. This class loads the mesh
* file, most times even in ascending order. This class loads the mesh
* offsets dictionary only once and keeps the stream open.
*
* Instances of this class are not thread safe.
*/
class MeshLoader {
public:
MeshLoader(const fs::path& filePath) {
m_fstream = new FileStream(filePath, FileStream::EReadOnly);
m_fstream->setByteOrder(Stream::ELittleEndian);
@ -264,6 +264,11 @@ private:
&boost::make_shared<MeshLoader, const fs::path&>) {}
};
/// Release all currently held offset caches / file streams
static void flushCache() {
m_cache.set(NULL);
}
/// Loads the mesh from the thread-local file stream cache
void loadCompressed(const fs::path& filePath, const int idx) {
if (EXPECT_NOT_TAKEN(idx < 0)) {
@ -276,6 +281,7 @@ private:
if (EXPECT_NOT_TAKEN(cache == NULL)) {
cache = new FileStreamCache();
m_cache.set(cache);
SceneHandler::pushCleanupHandler(&SerializedMesh::flushCache);
}
boost::shared_ptr<MeshLoader> meshLoader = cache->get(filePath);
@ -288,7 +294,6 @@ private:
ThreadLocal<SerializedMesh::FileStreamCache> SerializedMesh::m_cache;
MTS_IMPLEMENT_CLASS_S(SerializedMesh, false, TriMesh)
MTS_EXPORT_PLUGIN(SerializedMesh, "Serialized mesh loader");
MTS_NAMESPACE_END

View File

@ -58,7 +58,7 @@ public:
if (m_type == Properties::EFloat)
m_float = props.getFloat("value");
else if (m_type == Properties::EPoint)
else if (m_type == Properties::EVector)
m_vector = props.getVector("value");
else if (m_type == Properties::ESpectrum)
m_spectrum = props.getSpectrum("value");
@ -72,7 +72,7 @@ public:
m_type = stream->readInt();
if (m_type == Properties::EFloat)
m_float = stream->readFloat();
else if (m_type == Properties::EPoint)
else if (m_type == Properties::EVector)
m_vector = Vector(stream);
else if (m_type == Properties::ESpectrum)
m_spectrum = Spectrum(stream);