File: GB_AxB_saxpy5_meta.c

package info (click to toggle)
suitesparse-graphblas 7.4.0%2Bdfsg-1
  • links: PTS, VCS
  • area: main
  • in suites: bookworm
  • size: 67,112 kB
  • sloc: ansic: 1,072,243; cpp: 8,081; sh: 512; makefile: 503; asm: 369; python: 125; awk: 10
file content (145 lines) | stat: -rw-r--r-- 4,874 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
//------------------------------------------------------------------------------
// GB_AxB_saxpy5_meta.c: C+=A*B when C is full
//------------------------------------------------------------------------------

// SuiteSparse:GraphBLAS, Timothy A. Davis, (c) 2017-2022, All Rights Reserved.
// SPDX-License-Identifier: Apache-2.0

//------------------------------------------------------------------------------

// This method is only used for built-in semirings with no typecasting.
// The accumulator matches the semiring monoid.
// The ANY monoid is not supported.

// C is as-if-full.
// A is bitmap or full.
// B is sparse or hypersparse.

#if GB_IS_ANY_MONOID
#error "saxpy5 not defined for the ANY monoid"
#endif

{

    //--------------------------------------------------------------------------
    // get C, A, and B
    //--------------------------------------------------------------------------

    ASSERT (GB_as_if_full (C)) ;
    ASSERT (C->vlen == A->vlen) ;
    ASSERT (C->vdim == B->vdim) ;
    ASSERT (A->vdim == B->vlen) ;
    ASSERT (GB_IS_BITMAP (A) || GB_as_if_full (A)) ;
    ASSERT (GB_IS_SPARSE (B) || GB_IS_HYPERSPARSE (B)) ;

    const bool A_is_bitmap = GB_IS_BITMAP (A) ;

    //--------------------------------------------------------------------------
    // C += A*B, no mask, A bitmap/full, B sparse/hyper
    //--------------------------------------------------------------------------

    #if GB_A_IS_PATTERN
    {

        //----------------------------------------------------------------------
        // A is pattern-only
        //----------------------------------------------------------------------

        if (A_is_bitmap)
        {
            // A is bitmap and pattern-only
            #undef  GB_A_IS_BITMAP
            #define GB_A_IS_BITMAP 1
            #include "GB_AxB_saxpy5_iso_or_pattern.c"
        }
        else
        {
            // A is full and pattern-only
            #undef  GB_A_IS_BITMAP
            #define GB_A_IS_BITMAP 0
            #include "GB_AxB_saxpy5_iso_or_pattern.c"
        }

    }
    #else
    {

        //----------------------------------------------------------------------
        // A is valued
        //----------------------------------------------------------------------

        if (A->iso)
        {

            //------------------------------------------------------------------
            // A is iso-valued
            //------------------------------------------------------------------

            if (A_is_bitmap)
            { 
                // A is bitmap, iso-valued, B is sparse/hyper
                #undef  GB_A_IS_BITMAP
                #define GB_A_IS_BITMAP 1
                #include "GB_AxB_saxpy5_iso_or_pattern.c"
            }
            else
            { 
                // A is full, iso-valued, B is sparse/hyper
                #undef  GB_A_IS_BITMAP
                #define GB_A_IS_BITMAP 0
                #include "GB_AxB_saxpy5_iso_or_pattern.c"
            }

        }
        else
        {

            //------------------------------------------------------------------
            // general case: A is non-iso and valued
            //------------------------------------------------------------------

            if (A_is_bitmap)
            { 
                // A is bitmap, non-iso-valued, B is sparse/hyper
                #undef  GB_A_IS_BITMAP
                #define GB_A_IS_BITMAP 1
                #include "GB_AxB_saxpy5_bitmap.c"
                #undef  GB_A_IS_BITMAP
            }
            else
            { 
                // A is full, non-iso-valued, B is sparse/hyper
                #if GB_SEMIRING_HAS_AVX_IMPLEMENTATION          \
                    && GB_COMPILER_SUPPORTS_AVX512F             \
                    && GB_V4_512
                if (GB_Global_cpu_features_avx512f ( ))
                {
                    // x86_64 with AVX512f
                    GB_AxB_saxpy5_unrolled_avx512f (C, A, B,
                        ntasks, nthreads, B_slice, Context) ;
                    return (GrB_SUCCESS) ;
                }
                #endif
                #if GB_SEMIRING_HAS_AVX_IMPLEMENTATION          \
                    && GB_COMPILER_SUPPORTS_AVX2                \
                    && GB_V4_256
                if (GB_Global_cpu_features_avx2 ( ))
                {
                    // x86_64 with AVX2
                    GB_AxB_saxpy5_unrolled_avx2 (C, A, B,
                        ntasks, nthreads, B_slice, Context) ;
                    return (GrB_SUCCESS) ;
                }
                #endif
                // any architecture and any built-in semiring
                GB_AxB_saxpy5_unrolled_vanilla (C, A, B,
                    ntasks, nthreads, B_slice, Context) ;
            }
        }
    }
    #endif
}

#undef GB_A_IS_BITMAP
#undef GB_B_IS_HYPER