Hi,
Just to be sure, you modified the autograd.Function backward method in Linear to print this information?
A good way to see this is to rewrite the whole forward as just plain Functions:
# input that you gave the nn.Module
inp = torch.rand(10, 3) # Note that this ones does not require gradients
# Parameters for the first nn.Linear
fc1_weight = torch.rand(64, 3, requires_grad=True)
fc1_bias = torch.rand(64, requires_grad=True)
# Parameters for the second nn.Linear
fc2_weight = torch.rand(64, 64, requires_grad=True)
fc2_bias = torch.rand(64, requires_grad=True)

# What happens when you do FC()(input)
# I will write Function_Linear for the function that corresponds to the Linear layer
x = Function_Linear(inp, fc1_weight, fc1_bias)
# Note that x.requires_grad=True now
x = Function_Linear(x, fc1_weight, fc1_bias)

As you can see, for the first one, the tensors that are given, the first one does not require grads and the two others do. For the second one, all three require gradients.
So knowing which ones needs input gradient is a as simple as checking the requires_grad field for the input Tensors in the forward pass.
Now if you print during the backward, the backward of the second one is called first, then the backward of the first one.
Does that help?