pub fn cdef_filter_frame(fi: &FrameInvariants, rec: &mut Frame, bc: &mut BlockContext, bit_depth: usize) {

    // Each filter block is 64x64, except right and/or bottom for non-multiple-of-64 sizes.
    // FIXME: 128x128 SB support will break this, we need FilterBlockOffset etc.
    let fb_height = (fi.padded_h + 63) / 64;
    let fb_width = (fi.padded_w + 63) / 64;

    // Construct a padded copy of the reconstructed frame.
    let mut padded_px: [[usize; 2]; 3] = [[0; 2]; 3];
    for p in 0..3 {
        padded_px[p][0] =  (fb_width*64 >> rec.planes[p].cfg.xdec) + 4;
        padded_px[p][1] =  (fb_height*64 >> rec.planes[p].cfg.ydec) + 4;
    }
    let mut cdef_frame = Frame {
        planes: [
            Plane::new(padded_px[0][0], padded_px[0][1], rec.planes[0].cfg.xdec, rec.planes[0].cfg.ydec, 0, 0),
            Plane::new(padded_px[1][0], padded_px[1][1], rec.planes[1].cfg.xdec, rec.planes[1].cfg.ydec, 0, 0),
            Plane::new(padded_px[2][0], padded_px[2][1], rec.planes[2].cfg.xdec, rec.planes[2].cfg.ydec, 0, 0)
        ]
    };
    for p in 0..3 {
        let rec_w = fi.padded_w >> rec.planes[p].cfg.xdec;
        let rec_h = fi.padded_h >> rec.planes[p].cfg.ydec;
        for row in 0..padded_px[p][1] {
            // pad first two elements of current row
            {
                let mut cdef_slice = cdef_frame.planes[p].mut_slice(&PlaneOffset { x: 0, y: row as isize });
                let mut cdef_row = &mut cdef_slice.as_mut_slice()[..2];
                cdef_row[0] = CDEF_VERY_LARGE;
                cdef_row[1] = CDEF_VERY_LARGE;
            }
            // pad out end of current row
            {
                let mut cdef_slice = cdef_frame.planes[p].mut_slice(&PlaneOffset { x: rec_w as isize + 2, y: row as isize });
                let mut cdef_row = &mut cdef_slice.as_mut_slice()[..padded_px[p][0]-rec_w-2];
                for x in cdef_row {
                    *x = CDEF_VERY_LARGE;
                }
            }
            // copy current row from rec if we're in data, or pad if we're in first two rows/last N rows
            {
                let mut cdef_slice = cdef_frame.planes[p].mut_slice(&PlaneOffset { x: 2, y: row as isize });
                let mut cdef_row = &mut cdef_slice.as_mut_slice()[..rec_w];
                if row < 2 || row >= rec_h+2 {
                    for x in cdef_row {
                        *x = CDEF_VERY_LARGE;
                    }
                } else {
                    let rec_stride = rec.planes[p].cfg.stride;
                    cdef_row.copy_from_slice(&rec.planes[p].data_origin()[(row-2)*rec_stride..(row-1)*rec_stride][..rec_w]);
                }
            }
        }
    }

    // Perform actual CDEF, using the padded copy as source, and the input rec vector as destination.
    for fby in 0..fb_height {
        for fbx in 0..fb_width {
            let sbo = SuperBlockOffset { x: fbx, y: fby };
            let cdef_index = bc.at(&sbo.block_offset(0, 0)).cdef_index;
            let cdef_dirs = cdef_analyze_superblock(&mut cdef_frame, bc, &sbo, &sbo, bit_depth);
            cdef_filter_superblock(fi, &mut cdef_frame, rec, bc, &sbo, &sbo, bit_depth, cdef_index, &cdef_dirs);
        }
    }
}
// Input to this process is the array CurrFrame of reconstructed samples.
// Output from this process is the array CdefFrame containing deringed samples.
// The purpose of CDEF is to perform deringing based on the detected direction of blocks.
// CDEF parameters are stored for each 64 by 64 block of pixels.
// The CDEF filter is applied on each 8 by 8 block of pixels.
// Reference: http://av1-spec.argondesign.com/av1-spec/av1-spec.html#cdef-process
Input to this process is the array CurrFrame of reconstructed samples.
Output from this process is the array CdefFrame containing deringed samples.
The purpose of CDEF is to perform deringing based on the detected direction of blocks.
CDEF parameters are stored for each 64 by 64 block of pixels.
The CDEF filter is applied on each 8 by 8 block of pixels.
Input to this process is the array CurrFrame of reconstructed samples . Output from this process is the array CdefFrame containing deringed samples . The purpose of CDEF is to perform deringing based on the detected direction of blocks . CDEF parameters are stored for each 64 by 64 block of pixels . The CDEF filter is applied on each 8 by 8 block of pixels .
pub fn cdef_filter_frame(fi: &FrameInvariants, rec: &mut Frame, bc: &mut BlockContext, bit_depth: usize) {
    // Each filter block is 64x64, except right and/or bottom for non-multiple-of-64 sizes.
    // FIXME: 128x128 SB support will break this, we need FilterBlockOffset etc.
    let fb_height = (fi.padded_h + 63) / 64;
    let fb_width = (fi.padded_w + 63) / 64;
    // Construct a padded copy of the reconstructed frame.
    let mut padded_px: [[usize; 2]; 3] = [[0; 2]; 3];
    for p in 0..3 {
        padded_px[p][0] =  (fb_width*64 >> rec.planes[p].cfg.xdec) + 4;
        padded_px[p][1] =  (fb_height*64 >> rec.planes[p].cfg.ydec) + 4;
    }
    let mut cdef_frame = Frame {
        planes: [
            Plane::new(padded_px[0][0], padded_px[0][1], rec.planes[0].cfg.xdec, rec.planes[0].cfg.ydec, 0, 0),
            Plane::new(padded_px[1][0], padded_px[1][1], rec.planes[1].cfg.xdec, rec.planes[1].cfg.ydec, 0, 0),
            Plane::new(padded_px[2][0], padded_px[2][1], rec.planes[2].cfg.xdec, rec.planes[2].cfg.ydec, 0, 0)
        ]
    };
    for p in 0..3 {
        let rec_w = fi.padded_w >> rec.planes[p].cfg.xdec;
        let rec_h = fi.padded_h >> rec.planes[p].cfg.ydec;
        for row in 0..padded_px[p][1] {
            // pad first two elements of current row
            {
                let mut cdef_slice = cdef_frame.planes[p].mut_slice(&PlaneOffset { x: 0, y: row as isize });
                let mut cdef_row = &mut cdef_slice.as_mut_slice()[..2];
                cdef_row[0] = CDEF_VERY_LARGE;
                cdef_row[1] = CDEF_VERY_LARGE;
            }
            // pad out end of current row
            {
                let mut cdef_slice = cdef_frame.planes[p].mut_slice(&PlaneOffset { x: rec_w as isize + 2, y: row as isize });
                let mut cdef_row = &mut cdef_slice.as_mut_slice()[..padded_px[p][0]-rec_w-2];
                for x in cdef_row {
                    *x = CDEF_VERY_LARGE;
                }
            }
            // copy current row from rec if we're in data, or pad if we're in first two rows/last N rows
            {
                let mut cdef_slice = cdef_frame.planes[p].mut_slice(&PlaneOffset { x: 2, y: row as isize });
                let mut cdef_row = &mut cdef_slice.as_mut_slice()[..rec_w];
                if row < 2 || row >= rec_h+2 {
                    for x in cdef_row {
                        *x = CDEF_VERY_LARGE;
                    }
                } else {
                    let rec_stride = rec.planes[p].cfg.stride;
                    cdef_row.copy_from_slice(&rec.planes[p].data_origin()[(row-2)*rec_stride..(row-1)*rec_stride][..rec_w]);
                }
            }
        }
    }
    // Perform actual CDEF, using the padded copy as source, and the input rec vector as destination.
    for fby in 0..fb_height {
        for fbx in 0..fb_width {
            let sbo = SuperBlockOffset { x: fbx, y: fby };
            let cdef_index = bc.at(&sbo.block_offset(0, 0)).cdef_index;
            let cdef_dirs = cdef_analyze_superblock(&mut cdef_frame, bc, &sbo, &sbo, bit_depth);
            cdef_filter_superblock(fi, &mut cdef_frame, rec, bc, &sbo, &sbo, bit_depth, cdef_index, &cdef_dirs);
        }
    }
}
pub fn cdef_filter_frame ( fi : & FrameInvariants , rec : & mut Frame , bc : & mut BlockContext , bit_depth : usize ) { // Each filter block is 64x64, except right and/or bottom for non-multiple-of-64 sizes. // FIXME: 128x128 SB support will break this, we need FilterBlockOffset etc. let fb_height = ( fi . padded_h + 63 ) / 64 ; let fb_width = ( fi . padded_w + 63 ) / 64 ; // Construct a padded copy of the reconstructed frame. let mut padded_px : [ [ usize ; 2 ] ; 3 ] = [ [ 0 ; 2 ] ; 3 ] ; for p in 0 .. 3 { padded_px [ p ] [ 0 ] = ( fb_width * 64 >> rec . planes [ p ] . cfg . xdec ) + 4 ; padded_px [ p ] [ 1 ] = ( fb_height * 64 >> rec . planes [ p ] . cfg . ydec ) + 4 ; } let mut cdef_frame = Frame { planes : [ Plane :: new ( padded_px [ 0 ] [ 0 ] , padded_px [ 0 ] [ 1 ] , rec . planes [ 0 ] . cfg . xdec , rec . planes [ 0 ] . cfg . ydec , 0 , 0 ) , Plane :: new ( padded_px [ 1 ] [ 0 ] , padded_px [ 1 ] [ 1 ] , rec . planes [ 1 ] . cfg . xdec , rec . planes [ 1 ] . cfg . ydec , 0 , 0 ) , Plane :: new ( padded_px [ 2 ] [ 0 ] , padded_px [ 2 ] [ 1 ] , rec . planes [ 2 ] . cfg . xdec , rec . planes [ 2 ] . cfg . ydec , 0 , 0 ) ] } ; for p in 0 .. 3 { let rec_w = fi . padded_w >> rec . planes [ p ] . cfg . xdec ; let rec_h = fi . padded_h >> rec . planes [ p ] . cfg . ydec ; for row in 0 .. padded_px [ p ] [ 1 ] { // pad first two elements of current row { let mut cdef_slice = cdef_frame . planes [ p ] . mut_slice ( & PlaneOffset { x : 0 , y : row as isize } ) ; let mut cdef_row = & mut cdef_slice . as_mut_slice ( ) [ .. 2 ] ; cdef_row [ 0 ] = CDEF_VERY_LARGE ; cdef_row [ 1 ] = CDEF_VERY_LARGE ; } // pad out end of current row { let mut cdef_slice = cdef_frame . planes [ p ] . mut_slice ( & PlaneOffset { x : rec_w as isize + 2 , y : row as isize } ) ; let mut cdef_row = & mut cdef_slice . as_mut_slice ( ) [ .. padded_px [ p ] [ 0 ] - rec_w - 2 ] ; for x in cdef_row { * x = CDEF_VERY_LARGE ; } } // copy current row from rec if we're in data, or pad if we're in first two rows/last N rows { let mut cdef_slice = cdef_frame . planes [ p ] . mut_slice ( & PlaneOffset { x : 2 , y : row as isize } ) ; let mut cdef_row = & mut cdef_slice . as_mut_slice ( ) [ .. rec_w ] ; if row < 2 || row >= rec_h + 2 { for x in cdef_row { * x = CDEF_VERY_LARGE ; } } else { let rec_stride = rec . planes [ p ] . cfg . stride ; cdef_row . copy_from_slice ( & rec . planes [ p ] . data_origin ( ) [ ( row - 2 ) * rec_stride .. ( row - 1 ) * rec_stride ] [ .. rec_w ] ) ; } } } } // Perform actual CDEF, using the padded copy as source, and the input rec vector as destination. for fby in 0 .. fb_height { for fbx in 0 .. fb_width { let sbo = SuperBlockOffset { x : fbx , y : fby } ; let cdef_index = bc . at ( & sbo . block_offset ( 0 , 0 ) ) . cdef_index ; let cdef_dirs = cdef_analyze_superblock ( & mut cdef_frame , bc , & sbo , & sbo , bit_depth ) ; cdef_filter_superblock ( fi , & mut cdef_frame , rec , bc , & sbo , & sbo , bit_depth , cdef_index , & cdef_dirs ) ; } } }
Input to this process is the array CurrFrame of reconstructed samples.
Input to this process is the array CurrFrame of reconstructed samples .
fi
&FrameInvariants
rec
&mut Frame
bc
&mut BlockContext
bit_depth
usize