I finally managed to rasterize my model output before feeding it to the loss.backward() operation.
The solution is kind of nasty and requires to initialize the coordinate representation x in the shape of the pixel-wise representation, with x values occupying only a fraction of this shape. Then the rasterization function writes new values within the complete pixel-wise representation, from the few initialization values that it contains, coupled with the updated weights.
Here is the training protocol :
    # Training
    lr = 0.01
    for iepoch in range(nepochs):

        # get prediction
        ypred=mforward(x,w)

        # rasterize pred + test
        y=mrast(y,300,600)
        ypred=mrast(ypred,300,600)
        
        # update loss
        loss = get_loss(y, ypred)

        # get gradient
        loss.backward()
        
        # update weights
        with torch.no_grad():
            w -= lr * w.grad

        # reset gradient #37
        w.grad.zero_()

Here is the rasterization function :
def rasterize_toy3(tn,w,h):
    htn=torch.ones(nsamples,h,w,nc,dtype=torch.float)*0
    for i in range(nsamples): # for each sample
        top=(tn[i,0,0,0]*5).long()
        tn[i,top:,:,0]=100/255
        tn[i,top:,:,1]=100/255
        tn[i,top:,:,2]=100/255
    return tn

And here is the data initialisation function :
def set_data():
    
    ## data : origin
    if 1==0:
        x = torch.tensor([1, 2, 3, 4], dtype=torch.float32)
        y = torch.tensor([2, 4, 6, 8], dtype=torch.float32)
    
    ## data : alt
    if 1==1:
        
        nsamples,h,w,nc=4,60,30,3
        x=torch.ones(nsamples,h,w,nc,dtype=torch.float)*0
        x[:,0,0,0]=torch.tensor([1, 2, 3, 4], dtype=torch.float32)
        y=torch.ones(nsamples,h,w,nc,dtype=torch.float)*0
        y[:,0,0,0]=torch.tensor([2, 4, 6, 8], dtype=torch.float32)

    return x,y

If anyone has a more elegant solution, i’m interested.