This patch adds the `ptr.ptradd` and `ptr.type_offset` operations. Given
a `ptr` value these operations can be used to compute new addresses. For
example:
```mlir
func.func @ops0(%ptr: !ptr.ptr<#ptr.int_space>) -> !ptr.ptr<#ptr.int_space> {
%off = ptr.type_offset f32 : index
%res = ptr.ptradd %ptr, %off : !ptr.ptr<#ptr.int_space>, index
return %res : !ptr.ptr<#ptr.int_space>
}
```
Additionally, this patch also adds the `#ptr.generic_space`. This memory
space allows loading and storing values to all types.
---------
Co-authored-by: Mehdi Amini <joker.eph@gmail.com>
Co-authored-by: Tobias Gysi <tobias.gysi@nextsilicon.com>