Repository: pytorch
Issue: Wrong onnx model from `torch.onnx.export` when using `index_add_` function with duplicate `index` values.
Labels: module: onnx,triaged,module: advanced indexing

### 🐛 Describe the bug

I have noticed that `torch.onnx.export` produces wrong models if a module contains `Tensor.index_add_` function and the `index` parameter contains duplicate values. See the minimal example below:

```python
from typing import Sequence

import torch
from torch import nn
import onnx
import onnxruntime.backend as ort_backend
import numpy as np

class DummyModel(nn.Module):
    def forward(self, x: torch.Tensor, y: torch.Tensor, index: torch.Tensor) -> torch.Tensor:
        x.index_add_(0, index, y)
        return x

def test_model_equivalency(
    model: nn.Module, 
    input_tensors: Sequence[torch.Tensor],
) -> None:
    model.eval()
    with torch.no_grad():
        torch.onnx.export(model, input_tensors, "/tmp/dummy.onnx")
        onnx_output = ort_backend.run(
            onnx.load("/tmp/dummy.onnx"), 
            [x.detach().numpy() for x in input_tensors], 
            device="CPU"
        )[0]
        output = model(*input_tensors)
        np.testing.assert_almost_equal(output.detach().numpy(), onnx_output, decimal=5)

    print("PASS")

model = DummyModel()
```

When used with unique `index` values, the following test passes
```pyton
x = torch.randn(2)
y = torch.randn(2)
index = torch.Tensor([0, 1]).to(dtype=torch.int32)
test_model_equivalency(model, (x, y, index))
```
```bash
$ PASS
```

But when used with duplicate values, I get an error
```python
x = torch.randn(2)
y = torch.randn(2)
index = torch.Tensor([0, 0]).to(dtype=torch.int32)
test_model_equivalency(model, (x, y, index))
```
```bash
AssertionError: 
Arrays are not almost equal to 5 decimals

Mismatched elements: 1 / 2 (50%)
Max absolute difference: 0.44980058
Max relative difference: 1.523156
 x: array([0.74511, 1.51692], dtype=float32)
 y: array([0.29531, 1.51692], dtype=float32)
```

I understand that pytorch already emits warning about this (`torch/onnx/symbolic_opset9.py:3096: UserWarning: Warning: ONNX export does not support duplicated values in 'index' field, this will cause the ONNX model to be incorrect.`), but I am wondering what is the solution here? Should I avoid `index_add_` alltogether, and if so, is there a generic solution?


### Versions

```
PyTorch version: 1.9.0a0+gitd69c22d
Is debug build: False
CUDA used to build PyTorch: 11.1
ROCM used to build PyTorch: N/A

OS: Ubuntu 20.04.5 LTS (x86_64)
GCC version: (Ubuntu 9.4.0-1ubuntu1~20.04.2) 9.4.0
Clang version: Could not collect
CMake version: Could not collect
Libc version: glibc-2.31

Python version: 3.9.16 (main, Jan 11 2023, 16:05:54)  [GCC 11.2.0] (64-bit runtime)
Python platform: Linux-5.14.0-1058-oem-x86_64-with-glibc2.31
Is CUDA available: True
CUDA runtime version: Could not collect
CUDA_MODULE_LOADING set to: 
GPU models and configuration: 
GPU 0: NVIDIA GeForce RTX 2080 SUPER
GPU 1: NVIDIA GeForce RTX 2080 SUPER

Nvidia driver version: 525.125.06
cuDNN version: Could not collect
HIP runtime version: N/A
MIOpen runtime version: N/A
Is XNNPACK available: True

CPU:
Architecture:                    x86_64
CPU op-mode(s):                  32-bit, 64-bit
Byte Order:                      Little Endian
Address sizes:                   43 bits physical, 48 bits virtual
CPU(s):                          32
On-line CPU(s) list:             0-31
Thread(s) per core:              2
Core(s) per socket:              16
Socket(s):                       1
NUMA node(s):                    1
Vendor ID:                       AuthenticAMD
CPU family:                      23
Model:                           49
Model name:                      AMD Ryzen Threadripper PRO 3955WX 16-Cores
Stepping:                        0
Frequency boost:                 enabled
CPU MHz:                         2200.000
CPU max MHz:                     4402.7339
CPU min MHz:                     2200.0000
BogoMIPS:                        7785.58
Virtualization:                  AMD-V
L1d cache:                       512 KiB
L1i cache:                       512 KiB
L2 cache:                        8 MiB
L3 cache:                        64 MiB
NUMA node0 CPU(s):               0-31
Vulnerability Itlb multihit:     Not affected
Vulnerability L1tf:              Not affected
Vulnerability Mds:               Not affected
Vulnerability Meltdown:          Not affected
Vulnerability Mmio stale data:   Not affected
Vulnerability Spec store bypass: Mitigation; Speculative Store Bypass disabled via prctl and seccomp
Vulnerability Spectre v1:        Mitigation; usercopy/swapgs barriers and __user pointer sanitization
Vulnerability Spectre v2:        Mitigation; Retpolines, IBPB conditional, STIBP conditional, RSB filling
Vulnerability Srbds:             Not affected
Vulnerability Tsx async abort:   Not affected
Flags:                           fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 ht syscall nx mmxext fxsr_opt pdpe1gb rdtscp lm constant_tsc rep_good nopl nonstop_tsc cpuid extd_apicid aperfmperf rapl pni pclmulqdq monitor ssse3 fma cx16 sse4_1 sse4_2 x2apic movbe popcnt aes xsave avx f16c rdrand lahf_lm cmp_legacy svm extapic cr8_legacy abm sse4a misalignsse 3dnowprefetch osvw ibs skinit wdt tce topoext perfctr_core perfctr_nb bpext perfctr_llc mwaitx cpb cat_l3 cdp_l3 hw_pstate ssbd mba ibpb stibp vmmcall fsgsbase bmi1 avx2 smep bmi2 cqm rdt_a rdseed adx smap clflushopt clwb sha_ni xsaveopt xsavec xgetbv1 xsaves cqm_llc cqm_occup_llc cqm_mbm_total cqm_mbm_local clzero irperf xsaveerptr rdpru wbnoinvd arat npt lbrv svm_lock nrip_save tsc_scale vmcb_clean flushbyasid decodeassists pausefilter pfthreshold avic v_vmsave_vmload vgif v_spec_ctrl umip rdpid overflow_recov succor smca sme sev sev_es

Versions of relevant libraries:
[pip3] memory-efficient-attention-pytorch==0.0.17
[pip3] mypy==1.5.0
[pip3] mypy-boto3-s3==1.28.19
[pip3] mypy-extensions==1.0.0
[pip3] mypy-protobuf==3.5.0
[pip3] numpy==1.23.4
[pip3] pytorch-ignite==0.2.0
[pip3] pytorch-lightning==1.3.8
[pip3] torch==1.9.0+cu111.av3
[pip3] torch-scatter==2.0.9+av
[pip3] torch2trt==0.2.0
[pip3] torchmetrics==0.7.2
[pip3] torchview==0.2.6
[pip3] torchvision==0.10.0+av3
[pip3] torchviz==0.0.2
[conda] memory-efficient-attention-pytorch 0.0.17                   pypi_0    pypi
[conda] numpy                     1.23.4                   pypi_0    pypi
[conda] pytorch-ignite            0.2.0                    pypi_0    pypi
[conda] pytorch-lightning         1.3.8                    pypi_0    pypi
[conda] torch                     1.9.0+cu111.av3          pypi_0    pypi
[conda] torch-scatter             2.0.9+av                 pypi_0    pypi
[conda] torch2trt                 0.2.0                    pypi_0    pypi
[conda] torchmetrics              0.7.2                    pypi_0    pypi
[conda] torchview                 0.2.6                    pypi_0    pypi
[conda] torchvision               0.10.0+av3               pypi_0    pypi
[conda] torchviz                  0.0.2                    pypi_0    pypi
```