Jump to content

  • Log In with Google      Sign In   
  • Create Account

l0calh05t

Member Since 16 Dec 2000
Offline Last Active Dec 17 2014 06:11 PM

Topics I've Started

Visual C++ 2008 producing very strange code

02 August 2008 - 08:53 AM

I was looking at some assembler output and I noticed the following: This line of code (a and b are floats)
return a < b ? a : b;
creates the following output
movss	xmm0, DWORD PTR _a$[esp+8]
movss	xmm1, DWORD PTR _b$[esp+8]
cvtps2pd xmm0, xmm0
cvtps2pd xmm1, xmm1
comisd	xmm1, xmm0
lea	eax, DWORD PTR _a$[esp+8]
ja	SHORT $LN6@main
lea	eax, DWORD PTR _b$[esp+8]
$LN6@main:

I find it very strange that two single-precision floats are first expanded into double precision floats before being compared. Why isn't comiss used instead of comisd? This would save two instructions and would generally seem to be far more efficient.

implementing asynchronous calls

19 July 2008 - 01:50 PM

I implemented a fairly basic system for asynchronous calls (without return value, so no futures are needed. basically just injecting code into another thread). The purpose is to be able to call a function from one thread and have it executed in another. The system works (it's very basic), but there might be a better way I don't know about (which is why i'm posting here) AsyncCallable.hpp
#ifndef ASYNC_CALLABLE_HPP
#define ASYNC_CALLABLE_HPP

#include <vector>

#include <boost/function.hpp>
#include <boost/thread/mutex.hpp>

class AsyncCallable
{
protected:
	void appendCall(boost::function<void (void)> call);
	void executeCalls();

private:
	typedef std::vector<boost::function<void (void)> > call_vec;
	call_vec callsFront;
	call_vec callsBack;

	boost::mutex callMutex;
};

#endif

AsyncCallable.cpp
#include "AsyncCallable.hpp"

void AsyncCallable::appendCall(boost::function<void (void)> call)
{
	callMutex.lock();
	callsBack.push_back(call);
	callMutex.unlock();
}

void AsyncCallable::executeCalls()
{
	callMutex.lock();
	callsFront.swap(callsBack);
	callMutex.unlock();

	for(call_vec::iterator it = callsFront.begin(); it != callsFront.end(); ++it)
		(*it)();

	callsFront.resize(0);
}

A simple task using AsyncCallable:
class TestCallable : private AsyncCallable
{
public:
	TestCallable() : running(true) {}

	void run()
	{
		std::cout << "Howdy!\n";

		while(running)
		{
			executeCalls();

			std::cout << "Bla\n";
			Sleep(123);
		}

		std::cout << "Bye!\n";
	}

	void saySomething(const std::string& sth)
	{
		appendCall(boost::bind(&TestCallable::_saySomething,this,sth));
	}

	void stop()
	{
		appendCall(boost::bind(&TestCallable::_stop,this));
	}

private:
	bool running;

	void _saySomething(const std::string& sth)
	{
		std::cout << sth << "\n";
	}

	void _stop()
	{
		running = false;
	}
};


Interesting (new) programming languages

25 June 2008 - 11:58 AM

Since the code I wrote/am writing for my bachelor thesis makes use of automatic parallelism using OpenMP, I have become interested in languages that support implicit parallelism. So, today I was browsing the web trying to find current developments, and I found this one: Fortress: Sun's entry in the HPCS program. This one is very interesting IMHO. Although I'm a "Java hater", this language is absolutely great. Very nice operator overloading syntax, nice mathematical notation, support for task and data parallelism etc. The other HPCS program languages Chapel (Cray) and X10 (IBM) are interesting as well, though the notation isn't quite as nice as Fortress. Anyways, do you know any other interesting programming languages (not necessarily for parallel programming and not necessarily new, but no languages like Brainfuck and Malbolge please ;) )? Or comments on Fortress? Some others that come to mind are D (nice improvements over C++, but not big enough of an improvement to be worth the time, IMHO), Erlang (seems to be very good for network programming) and C++0x (ok, just a new standard, but with many much needed improvements, that is--if you're not using boost :P ) http://lambda-the-ultimate.org/node/1277

Why does this cause an error?

11 June 2008 - 04:34 AM

Minimal example:
void foo(const int** a)
{
	(void)a;
}

void bar(int** a)
{
	foo(a);
}

This causes a compiler error C2664 (compiler is VC++ 2008)
1>e:\development\softwareradio\modules\filter\dec_int\polyfir\main.cpp(22) : error C2664: 'foo' : cannot convert parameter 1 from 'int **' to 'const int **'
1>        Conversion loses qualifiers


Shouldn't casting from non-const to const be implicit? And single pointers do *not* cause this error... EDIT: And this works as well:
void foo(const int* const* a)
{
	(void)a;
}

void bar(int** a)
{
	foo(a);
}


Anisotropic BRDFs and normal mapping

15 February 2008 - 05:19 AM

I am currently experimenting with different BRDFs, and I've been wondering how to integrate anisotropic BRDFs with normal mapping. Anisotropic BRDFs generally require an orthonormal TBN basis, which would need to be modified according to the mapped normal vector. The only article I found on that topic was this one: http://ati.amd.com/developer/shaderx/ShaderX_PerPixelAniso.pdf which suggest subtracting the part of the tangent pointing in the direction of the normal (and renormalizing). Now, this works for most cases, but if the mapped normal is parallel to the original tangent (n.x = +-1) this obviously won't work. And if it is very close it could cause numerical precision problems. Does anyone have a suggestion for a solution which works in the general case? If anyone cares, the BRDF I want to apply this to the anisotropic phong brdf by Ashikhmin and Shirley.

PARTNERS