Problem
I wrote following code to check my understanding about these two functions
class LinearTransformation(nn.Module):
    def __init__(self, constant=False):
        super(LinearTransformation, self).__init__()
        self.linear = nn.Linear(2, 2)
        if constant:
            nn.init.constant(self.linear.weight, 10)
        else:
            nn.init.eye_(self.linear.weight)
        nn.init.constant_(self.linear.bias, 0)
    
    def forward(self, x):
        return torch.norm(self.linear(x)) ** 2

Invoking this simple class in the following snippets return
def hook(self, input):
    print(input)
model = LinearTransformation(constant=False)

x = torch.tensor([1., 2.])

model.linear.register_forward_pre_hook(hook)
model(x)
# (tensor([1., 2.]),)
# tensor(5., grad_fn=<PowBackward0>)

def hook(self, grad_input, grad_output):
    print(grad_input)
    print(grad_output)

model = LinearTransformation(constant=True)

x = torch.tensor([1., 2.])

model.linear.register_backward_hook(hook)
model(x).backward()
# (tensor([60., 60.]), tensor([60., 60.]))
# (tensor([60., 60.]),)

My questions are

For register_forward_pre_hook (first snippet), why 5, which is the final output, is also returned when I just register hook for nn.Linear.
For register_backward_hook (second snippet), I am not sure what these tensor([60, 60]) correspond to. I could see maybe grad_output is gradient respect to output of nn.Linear. But how about another two tensor([60, 60])?