Advertisement
Guest User

Untitled

a guest
Nov 17th, 2019
166
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 6.27 KB | None | 0 0
  1. #include <inttypes.h>
  2. #include <math.h>
  3. #include <stdbool.h>
  4. #include <stdio.h>
  5. #include <stdlib.h>
  6. #include <smmintrin.h>
  7. #include <xmmintrin.h>
  8.  
  9. const uint8_t INF_BYTES = 26;
  10.  
  11. bool read_pack(int n, FILE* f_in, FILE* f_out)
  12. {
  13.     uint8_t* a = (uint8_t*)_mm_malloc(n * sizeof(uint8_t), sizeof(uint8_t));
  14.     int readed = fread(a, sizeof(*a), n, f_in);
  15.     if (f_out != NULL) {
  16.         fwrite(a, sizeof(*a), readed, f_out);
  17.     }
  18.     _mm_free(a);
  19.     return readed == n;
  20. }
  21.  
  22. uint32_t read_information(FILE* fin,
  23.     FILE* fout,
  24.     int32_t* width,
  25.     int32_t* height)
  26. {
  27.     read_pack(10, fin, fout);
  28.     uint32_t bOffBits;
  29.     fread(&bOffBits, sizeof(uint32_t), 1, fin);
  30.  
  31.     if (fout != NULL) {
  32.         fwrite(&bOffBits, sizeof(bOffBits), 1, fout);
  33.     }
  34.     read_pack(4, fin, fout);
  35.    
  36.        
  37.     fread(width, sizeof(*width), 1, fin);
  38.     fread(height, sizeof(*height), 1, fin);
  39.     if (fout != NULL) {
  40.         fwrite(width, sizeof(*width), 1, fout);
  41.         fwrite(height, sizeof(*height), 1, fout);
  42.     }
  43.     return bOffBits;
  44. }
  45.  
  46. void read_from_file(
  47.     FILE* fin,
  48.     FILE* fout,
  49.     uint8_t*** color,
  50.     int32_t* width,
  51.     int32_t* height)
  52. {
  53.     uint32_t bOffBits = read_information(fin, fout, width, height);
  54.  
  55.     read_pack(bOffBits - INF_BYTES, fin, fout);
  56.  
  57.     (*color)[0] = (uint8_t*)_mm_malloc((*height) * (*width) * sizeof(uint8_t), sizeof(uint8_t));
  58.     (*color)[1] = (uint8_t*)_mm_malloc((*height) * (*width) * sizeof(uint8_t), sizeof(uint8_t));
  59.     (*color)[2] = (uint8_t*)_mm_malloc((*height) * (*width) * sizeof(uint8_t), sizeof(uint8_t));
  60.     (*color)[3] = (uint8_t*)_mm_malloc((*height) * (*width) * sizeof(uint8_t), sizeof(uint8_t));
  61.    
  62.     for (int32_t i = 0; i < (*height) * (*width); ++i) {
  63.         fread((*color)[0] + i, sizeof(uint8_t), 1, fin);
  64.         fread((*color)[1] + i, sizeof(uint8_t), 1, fin);
  65.         fread((*color)[2] + i, sizeof(uint8_t), 1, fin);
  66.         fread((*color)[3] + i, sizeof(uint8_t), 1, fin);
  67.     }
  68.  
  69. }
  70.  
  71. void recalculate(uint8_t** color1, int32_t width, int32_t height, uint8_t** color2)
  72. {
  73.     float* recalc = malloc(sizeof(float) * 4);
  74.    
  75.     for (int32_t i = 0; i < abs(height); ++i) {
  76.         for (int32_t j = 0; j + 4 < width; j += 4) {
  77.             int32_t ind = i * width + j;
  78.             color1[0][ind] = 255;
  79.             color1[0][ind + 1] = 255;
  80.             color1[0][ind + 2] = 255;
  81.             color1[0][ind + 3] = 255;
  82.            
  83.            
  84.             __m128 A2 = _mm_cvtepi32_ps(
  85.                        _mm_set_epi32(color2[0][ind + 3], color2[0][ind + 2], color2[0][ind + 1], color2[0][ind + 0]));
  86.             __m128 A2_255 = _mm_cvtepi32_ps(_mm_set_epi32(
  87.                        255 - color2[0][ind + 3], 255 - color2[0][ind + 2], 255 - color2[0][ind + 1], 255 - color2[0][ind]));
  88.             __m128 max = _mm_cvtepi32_ps(_mm_set_epi32(255, 255, 255, 255));
  89.            
  90.             __m128 col1 = _mm_cvtepi32_ps(
  91.                        _mm_set_epi32(color1[2][ind + 3], color1[2][ind + 2], color1[2][ind + 1], color1[2][ind + 0]));
  92.             __m128 col2 = _mm_cvtepi32_ps(
  93.                        _mm_set_epi32(color2[2][ind + 3], color2[2][ind + 2], color2[2][ind + 1], color2[2][ind + 0]));
  94.            
  95.             col1 = _mm_div_ps(_mm_add_ps(_mm_mul_ps(col1, A2_255), _mm_mul_ps(col2, A2)), max);
  96.             _mm_store_ps(recalc, col1);
  97.             color1[2][ind] = (uint8_t)recalc[0];
  98.             color1[2][ind + 1] = (uint8_t)recalc[1];
  99.             color1[2][ind + 2] = (uint8_t)recalc[2];
  100.             color1[2][ind + 3] = (uint8_t)recalc[3];
  101.            
  102.            
  103.            
  104.             col1 = _mm_cvtepi32_ps(
  105.                        _mm_set_epi32(color1[1][ind + 3], color1[1][ind + 2], color1[1][ind + 1], color1[1][ind + 0]));
  106.             col2 = _mm_cvtepi32_ps(
  107.                        _mm_set_epi32(color2[1][ind + 3], color2[1][ind + 2], color2[1][ind + 1], color2[1][ind + 0]));
  108.            
  109.             col1 = _mm_div_ps(_mm_add_ps(_mm_mul_ps(col1, A2_255), _mm_mul_ps(col2, A2)), max);
  110.             _mm_store_ps(recalc, col1);
  111.             color1[1][ind] = (uint8_t)recalc[0];
  112.             color1[1][ind + 1] = (uint8_t)recalc[1];
  113.             color1[1][ind + 2] = (uint8_t)recalc[2];
  114.             color1[1][ind + 3] = (uint8_t)recalc[3];
  115.          
  116.             col1 = _mm_cvtepi32_ps(
  117.                        _mm_set_epi32(color1[3][ind + 3], color1[3][ind + 2], color1[3][ind + 1], color1[3][ind + 0]));
  118.             col2 = _mm_cvtepi32_ps(
  119.                        _mm_set_epi32(color2[3][ind + 3], color2[3][ind + 2], color2[3][ind + 1], color2[3][ind + 0]));
  120.             col1 = _mm_div_ps(_mm_add_ps(_mm_mul_ps(col1, A2_255), _mm_mul_ps(col2, A2)), max);
  121.             _mm_store_ps(recalc, col1);
  122.             color1[3][ind] = (uint8_t)recalc[0];
  123.             color1[3][ind + 1] = (uint8_t)recalc[1];
  124.             color1[3][ind + 2] = (uint8_t)recalc[2];
  125.             color1[3][ind + 3] = (uint8_t)recalc[3];
  126.         }
  127.     }
  128.     _mm_free(recalc);
  129. }
  130.  
  131. void write_to_file(FILE* file, uint32_t height, uint32_t width, uint8_t** color1)
  132. {
  133.     for (int32_t i = 0; i < height * width; ++i) {
  134.         fwrite(color1[0] + i, sizeof(uint8_t), 1, file);
  135.         fwrite(color1[1] + i, sizeof(uint8_t), 1, file);
  136.         fwrite(color1[2] + i, sizeof(uint8_t), 1, file);
  137.         fwrite(color1[3] + i, sizeof(uint8_t), 1, file);
  138.     }
  139. }
  140.  
  141. void free_arr(uint8_t*** col)
  142. {
  143.     _mm_free((*col)[0]);
  144.     _mm_free((*col)[1]);
  145.     _mm_free((*col)[2]);
  146.     _mm_free((*col)[3]);
  147.     _mm_free(*col);
  148. }
  149.  
  150. int main(int argc, char* argv[])
  151. {
  152.     FILE* f1 = fopen(argv[1], "rb");
  153.     FILE* f2 = fopen(argv[2], "rb");
  154.     FILE* fout = fopen(argv[3], "wb");
  155.  
  156.    
  157.     uint8_t** color1 = (uint8_t**)_mm_malloc(4 * sizeof(uint8_t*), sizeof(uint8_t*));
  158.     int32_t width1;
  159.     int32_t height1;
  160.  
  161.     uint8_t** color2 = (uint8_t**)_mm_malloc(4 * sizeof(uint8_t*), sizeof(uint8_t*));
  162.     int32_t width2;
  163.     int32_t height2;
  164.  
  165.     read_from_file(f1, fout, &color1, &width1, &height1);
  166.     read_from_file(f2, NULL, &color2, &width2, &height2);
  167.  
  168.    
  169.     recalculate(color1, width1, height1, color2);
  170.  
  171.     write_to_file(fout, height1, width1, color1);
  172.    
  173.     while (read_pack(1000, f1, fout)) {
  174.         continue;
  175.     }
  176.    
  177.     free_arr(&color1);
  178.     free_arr(&color2);
  179.     return 0;
  180. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement