source: proto/s2k/trunk/demo/transpose/transpose_segment_at_a_time.cpp @ 4092

Last change on this file since 4092 was 3607, checked in by ksherdy, 5 years ago

Initial s2k Python demo library support. Refactor and organize Pablo Python libary code into a single library.

File size: 10.1 KB
Line 
1/**
2 * Transpose C++ demo.
3 *
4 * Author:   Ken Herdy
5 *
6 * Usage:    transpose <filename>
7 *
8 * Description:   
9 *
10 * Demonstrates both little endian bit order and big endian bit order s2p (segment-at-a-time).
11 *
12 * Final block only!
13 *
14 *
15 **/
16
17/**
18 * Platform independent runtime support libraries and C++ libraries.
19 **/
20#include <simd-lib/bitblock.hpp>
21#include <simd-lib/carryQ.hpp>
22#include <simd-lib/pabloSupport.hpp>
23#include <simd-lib/bitblock_iterator.hpp>
24#include <simd-lib/transpose.hpp>
25#include <stdio.h>
26#include <stdlib.h>
27
28static void s2p_le(BytePack b76543210_7, BytePack b76543210_6, BytePack b76543210_5, BytePack b76543210_4, 
29                      BytePack b76543210_3, BytePack b76543210_2, BytePack b76543210_1, BytePack b76543210_0, 
30                      BitBlock & b0, BitBlock & b1, BitBlock & b2, BitBlock & b3, 
31                      BitBlock & b4, BitBlock & b5, BitBlock & b6, BitBlock & b7) 
32{
33        BitBlock b7654_0, b7654_1, b7654_2, b7654_3;
34        BitBlock b3210_0, b3210_1, b3210_2, b3210_3;
35        BitBlock b76_0, b76_1, b54_0, b54_1;
36        BitBlock b32_0, b32_1, b10_0, b10_1;
37
38        b7654_3 = hsimd<8>::packh(b76543210_7, b76543210_6);
39        b7654_2 = hsimd<8>::packh(b76543210_5, b76543210_4);
40        b7654_1 = hsimd<8>::packh(b76543210_3, b76543210_2);
41        b7654_0 = hsimd<8>::packh(b76543210_1, b76543210_0);
42        b3210_3 = hsimd<8>::packl(b76543210_7, b76543210_6);
43        b3210_2 = hsimd<8>::packl(b76543210_5, b76543210_4);
44        b3210_1 = hsimd<8>::packl(b76543210_3, b76543210_2);
45        b3210_0 = hsimd<8>::packl(b76543210_1, b76543210_0);
46
47        b76_1 = hsimd<4>::packh(b7654_3, b7654_2);
48        b76_0 = hsimd<4>::packh(b7654_1, b7654_0);
49        b54_1 = hsimd<4>::packl(b7654_3, b7654_2);
50        b54_0 = hsimd<4>::packl(b7654_1, b7654_0);
51        b32_1 = hsimd<4>::packh(b3210_3, b3210_2);
52        b32_0 = hsimd<4>::packh(b3210_1, b3210_0);
53        b10_1 = hsimd<4>::packl(b3210_3, b3210_2);
54        b10_0 = hsimd<4>::packl(b3210_1, b3210_0);
55
56        b7 = hsimd<2>::packh(b76_1, b76_0);
57        b6 = hsimd<2>::packl(b76_1, b76_0);
58        b5 = hsimd<2>::packh(b54_1, b54_0);
59        b4 = hsimd<2>::packl(b54_1, b54_0);
60        b3 = hsimd<2>::packh(b32_1, b32_0);
61        b2 = hsimd<2>::packl(b32_1, b32_0);
62        b1 = hsimd<2>::packh(b10_1, b10_0);
63        b0 = hsimd<2>::packl(b10_1, b10_0);
64}
65
66#define s2p_ideal_le(s_7, s_6, s_5, s_4, s_3, s_2, s_1, s_0, r_0, r_1, r_2, r_3, r_4, r_5, r_6, r_7) \
67  do {\
68        BitBlock r_7654_3,r_7654_2,r_7654_1,r_7654_0;\
69  BitBlock r_3210_3,r_3210_2,r_3210_1,r_3210_0;\
70  BitBlock r_76_1,r_76_0,r_54_1,r_54_0;\
71        BitBlock r_32_1,r_32_0,r_10_1,r_10_0;\
72  r_7654_3 = hsimd<8>::packh(s_7, s_6);\
73        r_7654_2 = hsimd<8>::packh(s_5, s_4);\
74        r_7654_1 = hsimd<8>::packh(s_3, s_2);\
75        r_7654_0 = hsimd<8>::packh(s_1, s_0);\
76        r_3210_3 = hsimd<8>::packl(s_7, s_6);\
77        r_3210_2 = hsimd<8>::packl(s_5, s_4);\
78        r_3210_1 = hsimd<8>::packl(s_3, s_2);\
79        r_3210_0 = hsimd<8>::packl(s_1, s_0);\
80  r_76_1 = hsimd<4>::packh(r_7654_3, r_7654_2);\
81  r_76_0 = hsimd<4>::packh(r_7654_1, r_7654_0);\
82        r_54_1 = hsimd<4>::packl(r_7654_3, r_7654_2);\
83        r_54_0 = hsimd<4>::packl(r_7654_1, r_7654_0);\
84        r_32_1 = hsimd<4>::packh(r_3210_3, r_3210_2);\
85        r_32_0 = hsimd<4>::packh(r_3210_1, r_3210_0);\
86        r_10_1 = hsimd<4>::packl(r_3210_3, r_3210_2);\
87        r_10_0 = hsimd<4>::packl(r_3210_1, r_3210_0);\
88        r_7 = hsimd<2>::packh(r_76_1, r_76_0);\
89        r_6 = hsimd<2>::packl(r_76_1, r_76_0);\
90        r_5 = hsimd<2>::packh(r_54_1, r_54_0);\
91        r_4 = hsimd<2>::packl(r_54_1, r_54_0);\
92        r_3 = hsimd<2>::packh(r_32_1, r_32_0);\
93        r_2 = hsimd<2>::packl(r_32_1, r_32_0);\
94        r_1 = hsimd<2>::packh(r_10_1, r_10_0);\
95        r_0 = hsimd<2>::packl(r_10_1, r_10_0);\
96  } while(0)
97
98static void s2p_be(BytePack b76543210_7, BytePack b76543210_6, BytePack b76543210_5, BytePack b76543210_4, 
99                      BytePack b76543210_3, BytePack b76543210_2, BytePack b76543210_1, BytePack b76543210_0, 
100                      BitBlock & b0, BitBlock & b1, BitBlock & b2, BitBlock & b3, 
101                      BitBlock & b4, BitBlock & b5, BitBlock & b6, BitBlock & b7) 
102{
103        BitBlock b7654_0, b7654_1, b7654_2, b7654_3;
104        BitBlock b3210_0, b3210_1, b3210_2, b3210_3;
105        BitBlock b76_0, b76_1, b54_0, b54_1;
106        BitBlock b32_0, b32_1, b10_0, b10_1;
107
108        b7654_3 = hsimd<8>::packh(b76543210_7, b76543210_6);
109        b7654_2 = hsimd<8>::packh(b76543210_5, b76543210_4);
110        b7654_1 = hsimd<8>::packh(b76543210_3, b76543210_2);
111        b7654_0 = hsimd<8>::packh(b76543210_1, b76543210_0);
112        b3210_3 = hsimd<8>::packl(b76543210_7, b76543210_6);
113        b3210_2 = hsimd<8>::packl(b76543210_5, b76543210_4);
114        b3210_1 = hsimd<8>::packl(b76543210_3, b76543210_2);
115        b3210_0 = hsimd<8>::packl(b76543210_1, b76543210_0);
116
117        b76_1 = hsimd<4>::packh(b7654_3, b7654_2);
118        b76_0 = hsimd<4>::packh(b7654_1, b7654_0);
119        b54_1 = hsimd<4>::packl(b7654_3, b7654_2);
120        b54_0 = hsimd<4>::packl(b7654_1, b7654_0);
121        b32_1 = hsimd<4>::packh(b3210_3, b3210_2);
122        b32_0 = hsimd<4>::packh(b3210_1, b3210_0);
123        b10_1 = hsimd<4>::packl(b3210_3, b3210_2);
124        b10_0 = hsimd<4>::packl(b3210_1, b3210_0);
125
126        b0 = hsimd<2>::packh(b76_1, b76_0);
127        b1 = hsimd<2>::packl(b76_1, b76_0);
128        b2 = hsimd<2>::packh(b54_1, b54_0);
129        b3 = hsimd<2>::packl(b54_1, b54_0);
130        b4 = hsimd<2>::packh(b32_1, b32_0);
131        b5 = hsimd<2>::packl(b32_1, b32_0);
132        b6 = hsimd<2>::packh(b10_1, b10_0);
133        b7 = hsimd<2>::packl(b10_1, b10_0);
134}
135
136/**
137 * Platform independent type definitions.
138 **/
139typedef __m128i BitBlock;
140typedef BitBlock BytePack;
141typedef uint32_t scanblock_t;
142typedef uint32_t scanfield_t;
143
144/**
145 * Segment-at-a-time bufferd processing model parameters.
146 **/
147const int SCANBLOCK_SIZE   = (sizeof(scanblock_t) * 8);
148const int SCANFIELD_SIZE   = (sizeof(scanfield_t) * 8);
149// const int BLOCK_SIZE       =  (sizeof(BitBlock) * 8);                       
150const int SEGMENT_BLOCKS   = ((SCANBLOCK_SIZE * SCANFIELD_SIZE)/BLOCK_SIZE); 
151const int SEGMENT_SIZE     = (SEGMENT_BLOCKS * BLOCK_SIZE);
152const int CACHE_SIZE       = 32768;         
153const int BUFFER_SEGMENTS  = CACHE_SIZE / SEGMENT_SIZE;
154const int BUFFER_SIZE      = (BUFFER_SEGMENTS * SEGMENT_SIZE);
155
156BitBlock file_extent_mask(int size); 
157
158struct Basis_bits basis;
159
160/**
161 * Segment-at-a-time bufferd processing model parameters.
162 **/
163int bytes_read              = 0;
164int bytes_avail             = 0;
165
166int block                   = 0;
167int block_base              = 0; 
168
169int final_segment_size      = 0;
170int stream_pos              = 0;
171int match_index             = 0;
172
173int main(int argc, char * argv[])
174{
175  if ((2 > argc) || (2 < argc)) { printf("Usage: %s <filename>\n", argv[0]); exit(-1); } 
176 
177  char * infilename = argv[argc-1]; 
178  FILE * istream;
179  if((istream = fopen(infilename, "rb")) == NULL ) { printf("fopen error"); exit( 1 ); } 
180
181  BytePack * Byte; 
182  BitBlock aligned_buffer[BUFFER_SIZE]; 
183  char * buffer = (char *) aligned_buffer;
184 
185  /**
186    * Segment-at-a-time processing.
187    **/
188  while(!feof(istream)) 
189  { 
190    /**
191     * Read Stream in BUFFER_SIZE byte chunks.
192     **/
193    bytes_read  = fread(buffer, 1, BUFFER_SIZE, istream);
194    bytes_avail = bytes_read;
195
196    if(feof(istream)) { bytes_avail--; }
197    if(ferror(istream)) { perror( "io error" ); exit(1); }
198 
199    /**
200     * Process full segments
201     **/
202    block_base = 0;
203    while (bytes_avail >= SEGMENT_SIZE) 
204    {
205     
206      for(block=0; block<SEGMENT_BLOCKS; block++, block_base+=BLOCK_SIZE) 
207      {
208        //transpose.do_block(&buffer[block_base], basis);
209      }
210
211      bytes_avail -= SEGMENT_SIZE;     
212      stream_pos += SEGMENT_SIZE;
213    }   
214   
215    /**
216     * Process the final partial segment as full blocks then partial blocks.
217     **/ 
218    block = 0;
219    final_segment_size = bytes_avail;
220
221    /**
222     * Process full blocks.
223     **/
224    while (bytes_avail >= BLOCK_SIZE) 
225    {
226      //transpose.do_block(&buffer[block_base], basis);
227     
228      block_base += BLOCK_SIZE;
229      bytes_avail -= BLOCK_SIZE;
230      block++;
231    }
232
233    /**
234     * Process the final partial block.
235     **/
236    if(bytes_avail > 0) 
237    {
238      BitBlock FE_mask = file_extent_mask(bytes_avail);
239      //transpose.do_final_block(&buffer[block_base], basis, FE_mask);
240
241        BytePack * Byte = (BytePack *) buffer;
242
243                                printf("Little endian bit order\n");
244
245                                print_register<BytePack>("Byte", Byte[0]);
246
247        s2p_le(Byte[7], Byte[6], Byte[5], Byte[4], 
248            Byte[3], Byte[2], Byte[1], Byte[0],
249            basis.bit_0, basis.bit_1, basis.bit_2, basis.bit_3, 
250            basis.bit_4, basis.bit_5, basis.bit_6, basis.bit_7);
251
252                                basis.bit_7 = simd_and(basis.bit_7, FE_mask);
253                                basis.bit_6 = simd_and(basis.bit_6, FE_mask);
254                                basis.bit_5 = simd_and(basis.bit_5, FE_mask);
255                                basis.bit_4 = simd_and(basis.bit_4, FE_mask);
256                                basis.bit_3 = simd_and(basis.bit_3, FE_mask);
257                                basis.bit_2 = simd_and(basis.bit_2, FE_mask);
258                                basis.bit_1 = simd_and(basis.bit_1, FE_mask);
259                                basis.bit_0 = simd_and(basis.bit_0, FE_mask);
260
261                                print_register<BitBlock>("7", basis.bit_7);
262                                print_register<BitBlock>("6", basis.bit_6);
263                                print_register<BitBlock>("5", basis.bit_5);
264                                print_register<BitBlock>("4", basis.bit_4);
265                                print_register<BitBlock>("3", basis.bit_3);
266                                print_register<BitBlock>("2", basis.bit_2);
267                                print_register<BitBlock>("1", basis.bit_1);
268                                print_register<BitBlock>("0", basis.bit_0);
269
270                                printf("Big endian bit order\n");
271
272        s2p_be(Byte[7], Byte[6], Byte[5], Byte[4], 
273            Byte[3], Byte[2], Byte[1], Byte[0],
274            basis.bit_0, basis.bit_1, basis.bit_2, basis.bit_3, 
275            basis.bit_4, basis.bit_5, basis.bit_6, basis.bit_7);
276
277                                basis.bit_7 = simd_and(basis.bit_7, FE_mask);
278                                basis.bit_6 = simd_and(basis.bit_6, FE_mask);
279                                basis.bit_5 = simd_and(basis.bit_5, FE_mask);
280                                basis.bit_4 = simd_and(basis.bit_4, FE_mask);
281                                basis.bit_3 = simd_and(basis.bit_3, FE_mask);
282                                basis.bit_2 = simd_and(basis.bit_2, FE_mask);
283                                basis.bit_1 = simd_and(basis.bit_1, FE_mask);
284                                basis.bit_0 = simd_and(basis.bit_0, FE_mask);
285
286                                print_register<BitBlock>("7", basis.bit_7);
287                                print_register<BitBlock>("6", basis.bit_6);
288                                print_register<BitBlock>("5", basis.bit_5);
289                                print_register<BitBlock>("4", basis.bit_4);
290                                print_register<BitBlock>("3", basis.bit_3);
291                                print_register<BitBlock>("2", basis.bit_2);
292                                print_register<BitBlock>("1", basis.bit_1);
293                                print_register<BitBlock>("0", basis.bit_0);
294 
295    }
296
297    stream_pos += final_segment_size;
298   
299  }
300
301  fclose(istream);
302
303  return 0; 
304}
305
306BitBlock file_extent_mask(int size) {
307  return bitblock::srl(simd<1>::constant<1>(), convert(BLOCK_SIZE-size));
308}
309
Note: See TracBrowser for help on using the repository browser.