Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Faster checksum implementation #16372

Open
seanhess opened this issue May 2, 2024 · 1 comment
Open

Faster checksum implementation #16372

seanhess opened this issue May 2, 2024 · 1 comment

Comments

@seanhess
Copy link

seanhess commented May 2, 2024

What is the problem this feature will solve?

Astro.py currently takes several seconds to add a datasum to large fits files. In my tests using a 1.1GB fits file, where most of the data is in the primary HDU, it took ~2.5s to perform the following:

hdul = fits.open('inversion_output/scan1807/inv_res_pre.fits')
hdul[0].add_datasum()
hdul[0].header

Describe the desired outcome

While implementing this in Haskell, I used the c code in the FITS 4.0 spec, and adding a datasum to the same HDU was about 10x faster.

Code is included here. There are small differences from the code in the FITS 4.0 spec, namely returning the resulting sum instead of passing in a pointer.

unsigned int checksum (
  unsigned char *buf,
  int length)
{

  unsigned int sum32 = 0;
  unsigned int hi, lo, hicarry, locarry, i;

  // Accumulate the sum of the high-order 16 bits and the */
  // low-order 16 bits of each 32-bit word, separately. */
  // The first byte in each pair is the most significant. */
  // This algorithm works on both big and little endian machines.
  hi = (sum32 >> 16);
  lo = sum32 & 0xFFFF;
  for (i=0; i < length; i+=4) {
    hi += ((buf[i] << 8) + buf[i+1]);
    lo += ((buf[i+2] << 8) + buf[i+3]);
  }

  // fold carry bits from each 16 bit sum into the other sum
  hicarry = hi >> 16;
  locarry = lo >> 16;

  while (hicarry || locarry) {
    hi = (hi & 0xFFFF) + locarry;
    lo = (lo & 0xFFFF) + hicarry;
    hicarry = hi >> 16;
    locarry = lo >> 16;
  }

  // Concatenate the high and low parts to form the full 32-bit checksum
  return (hi << 16) + lo;
}

Additional context

No response

Copy link

github-actions bot commented May 2, 2024

Welcome to Astropy 👋 and thank you for your first issue!

A project member will respond to you as soon as possible; in the meantime, please double-check the guidelines for submitting issues and make sure you've provided the requested details.

GitHub issues in the Astropy repository are used to track bug reports and feature requests; If your issue poses a question about how to use Astropy, please instead raise your question in the Astropy Discourse user forum and close this issue.

If you feel that this issue has not been responded to in a timely manner, please send a message directly to the development mailing list. If the issue is urgent or sensitive in nature (e.g., a security vulnerability) please send an e-mail directly to the private e-mail feedback@astropy.org.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants