tensorflow / tfjs

A WebGL accelerated JavaScript library for training and deploying ML models.
https://js.tensorflow.org
Apache License 2.0
18.51k stars 1.93k forks source link

Incorrect values on created tensors (external WebGL context) #5601

Closed taoroalin closed 3 years ago

taoroalin commented 3 years ago

System information I'm using TFJS with an external WebGL context (using the WebGL backend). This is necessary to reproduce. Code is very custom. Windows 10 Chrome 92 TFJS v3.8.0 npm install @tensorflow/tfjs=3.8.0

Describe the current behavior When I create image tensors from Float32Arrays, every one I create beyond the first has the wrong values, which are way too high. For example, when I run tf.tensor(new Float32Array([123,32,111, ...]), [224,224,4]), I get the correct result, but the next time I run that (with a new input Float32Array) I get [133871614033920, 133062927056896, 246788401397760, -775327424, 4041891584, 241123305979904, 129437228072960, -817705664, ...], and each time I make another one of these the values are even bigger, and eventually they're all MAX_FLOAT(10^38). This only happens after I do an operation on the tensors, so when I construct them they're fine, but when I do tf.add(tensor, 0), the values are wrong.

Describe the expected behavior Newly created tensors would have the values given to them

Standalone code to reproduce the issue

import * as tf from "@tensorflow/tfjs"
import { setWebGLContext } from "@tensorflow/tfjs-backend-webgl";
import * as THREE from "three"
const main = async () => {
    const renderer = new THREE.WebGLRenderer({ antialias: true, powerPreference: 'high-performance' });

    const gl = renderer.getContext()
    setWebGLContext(2, gl);
    tf.setBackend('webgl')

    const scene = new THREE.Scene();
    const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);

    renderer.setSize(window.innerWidth, window.innerHeight);
    document.body.appendChild(renderer.domElement);
    const geometry = new THREE.BoxGeometry();
    const material = new THREE.MeshBasicMaterial({ color: 0x00ff00 });
    const cube = new THREE.Mesh(geometry, material);
    scene.add(cube);

    camera.position.z = 5;
    const render = () => renderer.render(scene, camera);
    render()

    const shape = [224, 224, 4]
    const size = shape.reduce((a, b) => a * b)
    for (let i = 0; i < 30; i++) {
        const array = new Float32Array(size)
        for (let i = 0; i < size; i++) {
            array[i] = i
        }
        const tensor = tf.tensor(array, shape)
        console.log(tensor.dataSync())
        const operatedOn = tf.add(tensor, 0)
        console.log(operatedOn.dataSync())
    }
}
main()
rthadur commented 3 years ago

@taoroalin can you please provide repro code in order for us to debug ? you can run the sample code in the any one of the boxes here https://js.tensorflow.org/api/latest/

taoroalin commented 3 years ago

Before I do that, do you know of any mechanisms for issues like this happening? Like what part of tfjs/webgl state might cause something like this?

pyu10055 commented 3 years ago

@taoroalin Looks like you are trying to use custom gl context, it might be better to register a new webgl backend:

   const backendName = 'three_webgl';
   setWebGLContext(2, gl);
    try {
      tf.registerBackend(backendName, () => {
        const context = new GPGPUContext(gl);
        return new MathBackendWebGL(context);
      }, 1);

      // Register all the webgl kernels on the three-webgl backend
      const kernels = tf.getKernelsForBackend('webgl');
      kernels.forEach(kernelConfig => {
        const newKernelConfig = Object.assign({}, kernelConfig, { backendName });
        tf.registerKernel(newKernelConfig);
      });
    } catch (e) {
      throw (new Error(`Failed to register Webgl backend: ${e.message}`));
    }
  }
  tf.setBackend(backendName);
google-ml-butler[bot] commented 3 years ago

Closing as stale. Please @mention us if this needs more attention.

google-ml-butler[bot] commented 3 years ago

Are you satisfied with the resolution of your issue? Yes No