github.com/lenartj/cfitsio@v0.0.0-20210325092924-ef692a403eb8/column.go (about) 1 package cfitsio 2 3 // #include <complex.h> 4 // #include "go-cfitsio.h" 5 // #include "go-cfitsio-utils.h" 6 import "C" 7 import ( 8 "fmt" 9 "reflect" 10 "unsafe" 11 ) 12 13 // Value is a value in a FITS table 14 type Value interface{} 15 16 // Column represents a column in a FITS table 17 type Column struct { 18 Name string // column name, corresponding to ``TTYPE`` keyword 19 Format string // column format, corresponding to ``TFORM`` keyword 20 Unit string // column unit, corresponding to ``TUNIT`` keyword 21 Null string // null value, corresponding to ``TNULL`` keyword 22 Bscale float64 // bscale value, corresponding to ``TSCAL`` keyword 23 Bzero float64 // bzero value, corresponding to ``TZERO`` keyword 24 Display string // display format, corresponding to ``TDISP`` keyword 25 Dim []int64 // column dimension corresponding to ``TDIM`` keyword 26 Start int64 // column starting position, corresponding to ``TBCOL`` keyword 27 Type TypeCode 28 Len int // repeat. if <= 1: scalar 29 Value Value // value at current row 30 } 31 32 // inferFormat infers the FITS format associated with a Column, according to its HDUType and Go type. 33 func (col *Column) inferFormat(htype HDUType) error { 34 var err error 35 if col.Format != "" { 36 return nil 37 } 38 39 str := gotype2FITS(col.Value, htype) 40 if str == "" { 41 return fmt.Errorf("cfitsio: %v can not handle [%T]", htype, col.Value) 42 } 43 col.Format = str 44 return err 45 } 46 47 // read reads the value at column number icol and row irow, into ptr. 48 // icol and irow are 0-based indices. 49 func (col *Column) read(f *File, icol int, irow int64, ptr interface{}) error { 50 var err error 51 52 c_type := C.int(0) 53 c_icol := C.int(icol + 1) // 0-based to 1-based index 54 c_irow := C.LONGLONG(irow + 1) // 0-based to 1-based index 55 56 c_len := C.LONGLONG(col.Len) 57 if col.Len <= 1 { 58 c_len = 1 59 } 60 61 var value interface{} 62 rv := reflect.Indirect(reflect.ValueOf(ptr)) 63 rt := reflect.TypeOf(rv.Interface()) 64 65 decode := func(c_type C.int, c_len C.LONGLONG, rt reflect.Type, scalar bool) (interface{}, error) { 66 var value interface{} 67 c_status := C.int(0) 68 c_anynul := C.int(0) 69 70 switch rt.Kind() { 71 case reflect.Bool: 72 c_type = C.TLOGICAL 73 v := make([]C.char, int(c_len), int(c_len)) 74 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 75 c_ptr := unsafe.Pointer(slice.Data) 76 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 77 if scalar { 78 value = v[0] == 1 79 } else { 80 vv := make([]bool, len(v), len(v)) 81 for ci, cv := range v { 82 vv[ci] = cv == 1 83 } 84 value = vv 85 } 86 87 case reflect.Uint8: 88 c_type = C.TBYTE 89 v := make([]uint8, int(c_len), int(c_len)) 90 value = v 91 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 92 c_ptr := unsafe.Pointer(slice.Data) 93 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 94 if scalar { 95 value = v[0] 96 } 97 98 case reflect.Uint16: 99 c_type = C.TUSHORT 100 v := make([]uint16, int(c_len), int(c_len)) 101 value = v 102 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 103 c_ptr := unsafe.Pointer(slice.Data) 104 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 105 if scalar { 106 value = v[0] 107 } 108 109 case reflect.Uint32: 110 c_type = C.TUINT 111 v := make([]uint32, int(c_len), int(c_len)) 112 value = v 113 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 114 c_ptr := unsafe.Pointer(slice.Data) 115 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 116 if scalar { 117 value = v[0] 118 } 119 120 case reflect.Uint64: 121 c_type = C.TULONG 122 v := make([]uint64, int(c_len), int(c_len)) 123 value = v 124 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 125 c_ptr := unsafe.Pointer(slice.Data) 126 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 127 if scalar { 128 value = v[0] 129 } 130 131 case reflect.Uint: 132 c_type = C.TULONG 133 v := make([]uint, int(c_len), int(c_len)) 134 value = v 135 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 136 c_ptr := unsafe.Pointer(slice.Data) 137 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 138 if scalar { 139 value = v[0] 140 } 141 142 case reflect.Int8: 143 c_type = C.TSBYTE 144 v := make([]int8, int(c_len), int(c_len)) 145 value = v 146 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 147 c_ptr := unsafe.Pointer(slice.Data) 148 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 149 if scalar { 150 value = v[0] 151 } 152 153 case reflect.Int16: 154 c_type = C.TSHORT 155 v := make([]int16, int(c_len), int(c_len)) 156 value = v 157 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 158 c_ptr := unsafe.Pointer(slice.Data) 159 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 160 if scalar { 161 value = v[0] 162 } 163 164 case reflect.Int32: 165 c_type = C.TINT 166 v := make([]int32, int(c_len), int(c_len)) 167 value = v 168 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 169 c_ptr := unsafe.Pointer(slice.Data) 170 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 171 if scalar { 172 value = v[0] 173 } 174 175 case reflect.Int64: 176 c_type = C.TLONG 177 v := make([]int64, int(c_len), int(c_len)) 178 value = v 179 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 180 c_ptr := unsafe.Pointer(slice.Data) 181 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 182 if scalar { 183 value = v[0] 184 } 185 186 case reflect.Int: 187 c_type = C.TLONG 188 v := make([]int, int(c_len), int(c_len)) 189 value = v 190 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 191 c_ptr := unsafe.Pointer(slice.Data) 192 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 193 if scalar { 194 value = v[0] 195 } 196 197 case reflect.Float32: 198 c_type = C.TFLOAT 199 v := make([]float32, int(c_len), int(c_len)) 200 value = v 201 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 202 c_ptr := unsafe.Pointer(slice.Data) 203 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 204 if scalar { 205 value = v[0] 206 } 207 208 case reflect.Float64: 209 c_type = C.TDOUBLE 210 v := make([]float64, int(c_len), int(c_len)) 211 value = v 212 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 213 c_ptr := unsafe.Pointer(slice.Data) 214 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 215 if scalar { 216 value = v[0] 217 } 218 219 case reflect.Complex64: 220 c_type = C.TCOMPLEX 221 v := make([]complex64, int(c_len), int(c_len)) // FIXME: assume same binary layout 222 value = v 223 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 224 c_ptr := unsafe.Pointer(slice.Data) 225 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 226 if scalar { 227 value = v[0] 228 } 229 230 case reflect.Complex128: 231 c_type = C.TDBLCOMPLEX 232 v := make([]complex128, int(c_len), int(c_len)) // FIXME: assume same binary layout 233 value = v 234 slice := (*reflect.SliceHeader)((unsafe.Pointer(&v))) 235 c_ptr := unsafe.Pointer(slice.Data) 236 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, c_len, nil, c_ptr, &c_anynul, &c_status) 237 if scalar { 238 value = v[0] 239 } 240 241 case reflect.String: 242 c_type = C.TSTRING 243 // FIXME: get correct maximum size from card 244 c_value := C.CStringN(C.FLEN_FILENAME) 245 defer C.free(unsafe.Pointer(c_value)) 246 c_ptr := unsafe.Pointer(&c_value) 247 C.fits_read_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, c_ptr, &c_anynul, &c_status) 248 value = C.GoString(c_value) 249 250 default: 251 return value, fmt.Errorf("cfitsio: invalid type [%v]", rt) 252 } 253 254 if c_status > 0 { 255 err = to_err(c_status) 256 return value, err 257 } 258 return value, nil 259 } 260 261 switch rt.Kind() { 262 263 case reflect.Slice: 264 c_len := C.long(0) 265 if col.Type < 0 { 266 c_off := C.long(0) 267 c_status := C.int(0) 268 C.fits_read_descript(f.c, c_icol, c_irow, &c_len, &c_off, &c_status) 269 if c_status > 0 { 270 err = to_err(c_status) 271 return err 272 } 273 } else { 274 c_len = C.long(col.Len) 275 } 276 scalar := false 277 value, err = decode(c_type, C.LONGLONG(c_len), rt.Elem(), scalar) 278 279 rv.Set(reflect.ValueOf(value)) 280 col.Value = rv.Interface() 281 282 case reflect.Array: 283 c_len := C.long(rt.Len()) 284 scalar := false 285 value, err = decode(c_type, C.LONGLONG(c_len), rt.Elem(), scalar) 286 287 // FIXME: unnecessary copy 288 array := reflect.New(rt).Elem() 289 reflect.Copy(array, reflect.ValueOf(value)) 290 rv.Set(array) 291 col.Value = rv.Interface() 292 293 case reflect.Bool, 294 reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, 295 reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, 296 reflect.Float32, reflect.Float64, 297 reflect.Complex64, reflect.Complex128, 298 reflect.String: 299 300 scalar := true 301 value, err = decode(c_type, C.LONGLONG(c_len), rt, scalar) 302 303 rv.Set(reflect.ValueOf(value)) 304 col.Value = rv.Interface() 305 306 default: 307 return fmt.Errorf("cfitsio: invalid type [%v]", rt) 308 } 309 310 return err 311 } 312 313 // write writes the current value of this Column into file f at column icol and row irow. 314 // icol and irow are 0-based indices. 315 func (col *Column) write(f *File, icol int, irow int64, value interface{}) error { 316 var err error 317 318 c_type := C.int(0) 319 c_icol := C.int(icol + 1) // 0-based to 1-based index 320 c_irow := C.LONGLONG(irow + 1) // 0-based to 1-based index 321 c_status := C.int(0) 322 323 rv := reflect.ValueOf(value) 324 rt := reflect.TypeOf(value) 325 326 switch rt.Kind() { 327 case reflect.Bool: 328 c_type = C.TLOGICAL 329 c_value := C.char(0) // 'F' 330 if value.(bool) { 331 c_value = 1 332 } 333 c_ptr := unsafe.Pointer(&c_value) 334 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 335 336 case reflect.Uint8: 337 c_type = C.TBYTE 338 c_value := C.char(value.(byte)) 339 c_ptr := unsafe.Pointer(&c_value) 340 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 341 342 case reflect.Uint16: 343 c_type = C.TUSHORT 344 c_value := C.ushort(value.(uint16)) 345 c_ptr := unsafe.Pointer(&c_value) 346 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 347 348 case reflect.Uint32: 349 c_type = C.TUINT 350 c_value := C.uint(value.(uint32)) 351 c_ptr := unsafe.Pointer(&c_value) 352 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 353 354 case reflect.Uint64: 355 c_type = C.TULONG 356 c_value := C.ulong(value.(uint64)) 357 c_ptr := unsafe.Pointer(&c_value) 358 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 359 360 case reflect.Uint: 361 c_type = C.TULONG 362 c_value := C.ulong(value.(uint)) 363 c_ptr := unsafe.Pointer(&c_value) 364 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 365 366 case reflect.Int8: 367 c_type = C.TSBYTE 368 c_value := C.char(value.(int8)) 369 c_ptr := unsafe.Pointer(&c_value) 370 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 371 372 case reflect.Int16: 373 c_type = C.TSHORT 374 c_value := C.short(value.(int16)) 375 c_ptr := unsafe.Pointer(&c_value) 376 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 377 378 case reflect.Int32: 379 c_type = C.TINT 380 c_value := C.int(value.(int32)) 381 c_ptr := unsafe.Pointer(&c_value) 382 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 383 384 case reflect.Int64: 385 c_type = C.TLONG 386 c_value := C.long(value.(int64)) 387 c_ptr := unsafe.Pointer(&c_value) 388 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 389 390 case reflect.Int: 391 c_type = C.TLONG 392 c_value := C.long(value.(int)) 393 c_ptr := unsafe.Pointer(&c_value) 394 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 395 396 case reflect.Float32: 397 c_type = C.TFLOAT 398 c_value := C.float(value.(float32)) 399 c_ptr := unsafe.Pointer(&c_value) 400 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 401 402 case reflect.Float64: 403 c_type = C.TDOUBLE 404 c_value := C.double(value.(float64)) 405 c_ptr := unsafe.Pointer(&c_value) 406 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 407 408 case reflect.Complex64: 409 c_type = C.TCOMPLEX 410 value := value.(complex64) 411 c_ptr := unsafe.Pointer(&value) // FIXME: assumes same memory layout 412 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 413 414 case reflect.Complex128: 415 c_type = C.TDBLCOMPLEX 416 value := value.(complex128) 417 c_ptr := unsafe.Pointer(&value) // FIXME: assumes same memory layout 418 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 419 420 case reflect.String: 421 c_type = C.TSTRING 422 c_value := C.CString(value.(string)) 423 defer C.free(unsafe.Pointer(c_value)) 424 c_ptr := unsafe.Pointer(&c_value) 425 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, 1, c_ptr, &c_status) 426 427 case reflect.Slice: 428 switch rt.Elem().Kind() { 429 case reflect.Bool: 430 c_type = C.TLOGICAL 431 value := value.([]bool) 432 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 433 c_ptr := unsafe.Pointer(slice.Data) 434 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 435 436 case reflect.Uint8: 437 c_type = C.TBYTE 438 value := value.([]uint8) 439 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 440 c_ptr := unsafe.Pointer(slice.Data) 441 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 442 443 case reflect.Uint16: 444 c_type = C.TUSHORT 445 value := value.([]uint16) 446 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 447 c_ptr := unsafe.Pointer(slice.Data) 448 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 449 450 case reflect.Uint32: 451 c_type = C.TUINT 452 value := value.([]uint32) 453 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 454 c_ptr := unsafe.Pointer(slice.Data) 455 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 456 457 case reflect.Uint64: 458 c_type = C.TULONG 459 value := value.([]uint64) 460 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 461 c_ptr := unsafe.Pointer(slice.Data) 462 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 463 464 case reflect.Uint: 465 c_type = C.TULONG 466 value := value.([]uint) 467 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 468 c_ptr := unsafe.Pointer(slice.Data) 469 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 470 471 case reflect.Int8: 472 c_type = C.TSBYTE 473 value := value.([]int8) 474 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 475 c_ptr := unsafe.Pointer(slice.Data) 476 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 477 478 case reflect.Int16: 479 c_type = C.TSHORT 480 value := value.([]int16) 481 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 482 c_ptr := unsafe.Pointer(slice.Data) 483 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 484 485 case reflect.Int32: 486 c_type = C.TINT 487 value := value.([]int32) 488 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 489 c_ptr := unsafe.Pointer(slice.Data) 490 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 491 492 case reflect.Int64: 493 c_type = C.TLONG 494 value := value.([]int64) 495 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 496 c_ptr := unsafe.Pointer(slice.Data) 497 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 498 499 case reflect.Int: 500 c_type = C.TLONG 501 value := value.([]int) 502 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 503 c_ptr := unsafe.Pointer(slice.Data) 504 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 505 506 case reflect.Float32: 507 c_type = C.TFLOAT 508 value := value.([]float32) 509 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 510 c_ptr := unsafe.Pointer(slice.Data) 511 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 512 513 case reflect.Float64: 514 c_type = C.TDOUBLE 515 value := value.([]float64) 516 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) 517 c_ptr := unsafe.Pointer(slice.Data) 518 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 519 520 case reflect.Complex64: 521 c_type = C.TCOMPLEX 522 value := value.([]complex64) 523 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) // FIXME: assume same bin-layout 524 c_ptr := unsafe.Pointer(slice.Data) 525 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 526 527 case reflect.Complex128: 528 c_type = C.TDBLCOMPLEX 529 value := value.([]complex128) 530 slice := (*reflect.SliceHeader)((unsafe.Pointer(&value))) // FIXME: assume same bin-layout 531 c_ptr := unsafe.Pointer(slice.Data) 532 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, C.LONGLONG(slice.Len), c_ptr, &c_status) 533 default: 534 panic(fmt.Errorf("unhandled type '%T'", value)) 535 } 536 537 case reflect.Array: 538 539 // FIXME: unnecessary copy 540 arr := reflect.New(rv.Type()).Elem() 541 reflect.Copy(arr, rv) 542 ptr := arr.Addr() 543 c_ptr := unsafe.Pointer(ptr.Pointer()) 544 c_len := C.LONGLONG(rt.Len()) 545 546 switch rt.Elem().Kind() { 547 case reflect.Bool: 548 c_type = C.TLOGICAL 549 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 550 551 case reflect.Uint8: 552 c_type = C.TBYTE 553 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 554 555 case reflect.Uint16: 556 c_type = C.TUSHORT 557 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 558 559 case reflect.Uint32: 560 c_type = C.TUINT 561 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 562 563 case reflect.Uint64: 564 c_type = C.TULONG 565 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 566 567 case reflect.Uint: 568 c_type = C.TULONG 569 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 570 571 case reflect.Int8: 572 c_type = C.TSBYTE 573 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 574 575 case reflect.Int16: 576 c_type = C.TSHORT 577 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 578 579 case reflect.Int32: 580 c_type = C.TINT 581 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 582 583 case reflect.Int64: 584 c_type = C.TLONG 585 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 586 587 case reflect.Int: 588 c_type = C.TLONG 589 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 590 591 case reflect.Float32: 592 c_type = C.TFLOAT 593 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 594 595 case reflect.Float64: 596 c_type = C.TDOUBLE 597 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 598 599 case reflect.Complex64: 600 c_type = C.TCOMPLEX 601 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 602 603 case reflect.Complex128: 604 c_type = C.TDBLCOMPLEX 605 C.fits_write_col(f.c, c_type, c_icol, c_irow, 1, c_len, c_ptr, &c_status) 606 default: 607 panic(fmt.Errorf("unhandled type '%T'", value)) 608 } 609 610 default: 611 panic(fmt.Errorf("unhandled type '%T' (%v)", value, rt.Kind())) 612 } 613 614 if c_status > 0 { 615 err = to_err(c_status) 616 } 617 618 return err 619 } 620 621 // EOF