Point light illuminating only half of a scene

A point light is illuminating only a half of a scene in my small 3D renderer. It happens on every scene I've tried (conference room, cornell box, etc).

How do I go about debugging this? What could be wrong?

Here are the shaders. I'm not doing anything out of the ordinary. Light is positioned at (0, 1.0, 0) in world space.

//
//
#version 410 core

uniform mat4 M;
uniform mat4 V;
uniform mat4 P;

layout (location = 0) in vec3 position;
layout (location = 1) in vec3 normal;
layout (location = 2) in vec3 color;
layout (location = 3) in vec2 texCoords;

out vec3 fWorldPos;
out vec3 fNormal;
out vec3 fColor;
out vec2 fTexCoords;

void main()
{
mat4 normalMatrix = transpose(inverse(M));

fWorldPos = vec3(M * vec4(position, 1.0));
fNormal = normal; // also tested multiplying with normal, M, and MV matrices
fColor = color;
fTexCoords = texCoords;

gl_Position = P * V * M * vec4(position, 1);
}

//
//
#version 410 core
#define MAX_POINT_LIGHTS 4

struct PointLight {
float strength;
vec3 position;
vec3 color;
vec3 attenuation;
};

struct Material {
vec3 color;
};

uniform Material material;
uniform int totalPointLights;
uniform PointLight pointLights[MAX_POINT_LIGHTS];
uniform vec3 cameraPosition;

in vec3 fWorldPos;
in vec3 fNormal;
in vec3 fColor;
in vec2 fTexCoords;

out vec4 color;

float attenuate(float dist, const PointLight light) {
return light.strength / (light.attenuation.x + light.attenuation.y * dist + light.attenuation.z * dist * dist);
}

//
// MAIN
//
void main()
{
vec3 normal = normalize(fNormal);

PointLight light = pointLights[0];

vec3 lightDir = light.position - fWorldPos;
float lightDst = length(lightDir);
lightDir = lightDir / lightDst;

float att = attenuate(lightDst, light);
float diffuseFactor = max(dot(normal, lightDir), 0.0);

color = vec4(material.color * diffuseFactor * att, 1);
}
$$$$
`
• is this a raytracer or something? If so can you try to disable shadows and see if it renders everything then? It happened with me once due to incorrect intersection testing and it was thinking that the lit surface was in shadow – gallickgunner Jan 21 at 19:33
• @gallickgunner No, it's just a regular forward renderer. It loads a scene from an .obj -file and renders it using the shader above. There are no shadows yet. Thanks though. – Ohkomonkiainen Jan 21 at 19:50
• Quick thought, it may be because of the diffuseFactor term or the att term going to zero. Did you try inverting the normals or the light direction and see how does it look then? You can also try to just set the material color and add terms one by one so as to figure out which factor is causing the problem – gallickgunner Jan 21 at 22:31
• Wrong normals perhaps? Test with M == identity to see if that's the problem. You should transform the normal with the transpose of the inverse matrix. And then normalize it again. – Olivier Jan 22 at 1:56