This is a simple/standard [square] matrix rotation. I worked this out by hand using graph paper and physically rotating it.
For counterclockwise (rotate left), the equation is:
out[7-x][y] = inp[y][x];
For clockwise (rotate right), the equation is:
out[x][7-y] = inp[y][x];
... except that we have to extract bits in the X dimension, so we need some functions that simulate the matrix access for bits.
Here's a test program with the necessary functions:
#include <stdio.h>
typedef unsigned char byte;
typedef void (*rot_p)(byte *dst,const byte *src);
#define MSK(_shf) (1 << (7 - (_shf)))
byte result[8];
// original matrix
byte rows[8] = {
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b11111111
};
// counterclockwise (rotate left)
byte rows2[8] = {
0b11111111,
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b00000001,
0b00000001
};
// clockwise (rotate right)
byte rows3[8] = {
0b10000000,
0b10000000,
0b10000000,
0b10000000,
0b10000000,
0b10000000,
0b10000000,
0b11111111
};
// bitget -- get bit from matrix
byte
bitget(const byte *rows,int y,int x)
{
byte val;
rows += y;
val = *rows;
val &= MSK(x);
return val;
}
// bitget -- set bit in matrix
void
bitset(byte *rows,int y,int x,byte val)
{
byte msk;
rows += y;
msk = MSK(x);
if (val)
*rows |= msk;
else
*rows &= ~msk;
}
// rotright -- rotate matrix right (clockwise)
void
rotright(byte *dst,const byte *src)
{
int x;
int y;
byte val;
for (y = 0; y < 8; ++y) {
for (x = 0; x < 8; ++x) {
val = bitget(src,y,x);
bitset(dst,x,7 - y,val);
}
}
}
// rotleft -- rotate matrix left (counterclockwise)
void
rotleft(byte *dst,const byte *src)
{
int x;
int y;
byte val;
for (y = 0; y < 8; ++y) {
for (x = 0; x < 8; ++x) {
val = bitget(src,y,x);
bitset(dst,7 - x,y,val);
}
}
}
// mtxshow -- print matrix
void
mtxshow(const byte *mtx,const char *sym,const char *tag)
{
int y;
int x;
byte val;
printf("%s/%s:\n",sym,tag);
for (y = 0; y < 8; ++y) {
printf(" ");
for (x = 0; x < 8; ++x) {
val = bitget(mtx,y,x);
val = val ? '1' : '0';
fputc(val,stdout);
}
fputc('\n',stdout);
}
}
// test -- perform test
void
test(const byte *exp,rot_p fnc,const char *tag)
{
printf("\n");
mtxshow(exp,tag,"expected");
fnc(result,rows);
mtxshow(result,tag,"actual");
}
int
main(void)
{
mtxshow(rows,"rows","orig");
test(rows2,rotleft,"rotleft");
test(rows3,rotright,"rotright");
return 0;
}
Here's the program output:
rows/orig:
00000001
00000001
00000001
00000001
00000001
00000001
00000001
11111111
rotleft/expected:
11111111
00000001
00000001
00000001
00000001
00000001
00000001
00000001
rotleft/actual:
11111111
00000001
00000001
00000001
00000001
00000001
00000001
00000001
rotright/expected:
10000000
10000000
10000000
10000000
10000000
10000000
10000000
11111111
rotright/actual:
10000000
10000000
10000000
10000000
10000000
10000000
10000000
11111111