diff --git a/CMakeLists.txt b/CMakeLists.txt
index 1170c16e4f122ea0bb17f44dd156a9504ecb226b..b5220b006ad9bd500054aae4d37e5580533fe45b 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -70,6 +70,7 @@ if (MORSE_DISTRIB_DIR OR EXISTS "${CMAKE_SOURCE_DIR}/CMakeModules/morse/")
   option( SCALFMM_USE_MIC_NATIVE       "Set to ON to compile in native mode for MIC" OFF  )
   option( SCALFMM_ONLY_DEVEL           "Set to ON to compile Development tools (only scalfmm team)" ON )
   if( SCALFMM_ONLY_DEVEL )
+    option( OPENMP_SUPPORT_COMMUTE   "Set to ON to let tasks commute (KSTAR/StarPU compiler only)" OFF )
     option( SCALFMM_USE_STARPU  "Set to ON to build SCALFMM with StarPU" OFF )
     option( SCALFMM_BUILD_UTILS "Set to ON to build utils Tests"    OFF )
   endif()
diff --git a/Src/GroupTree/Core/FGroupTaskDepAlgorithm.hpp b/Src/GroupTree/Core/FGroupTaskDepAlgorithm.hpp
index 80f7241799d9abb39f065bad3e5b4e35bc028254..b44b6b2b65e0614530dd57ff22eaccef9a42c3c1 100644
--- a/Src/GroupTree/Core/FGroupTaskDepAlgorithm.hpp
+++ b/Src/GroupTree/Core/FGroupTaskDepAlgorithm.hpp
@@ -405,7 +405,11 @@ protected:
                     PoleCellClass* cellPoles = currentCells->getRawMultipoleBuffer();
                     LocalCellClass* cellLocals = currentCells->getRawLocalBuffer();
 
+#ifdef OPENMP_SUPPORT_COMMUTE
+                    #pragma omp task default(none) firstprivate(currentCells, cellPoles, cellLocals, idxLevel) depend(commute: cellLocals[0]) depend(in: cellPoles[0])
+#else
                     #pragma omp task default(none) firstprivate(currentCells, cellPoles, cellLocals, idxLevel) depend(inout: cellLocals[0]) depend(in: cellPoles[0])
+#endif
                     {
                         const MortonIndex blockStartIdx = currentCells->getStartingIndex();
                         const MortonIndex blockEndIdx = currentCells->getEndingIndex();
@@ -467,7 +471,11 @@ protected:
                         LocalCellClass* cellOtherLocals = cellsOther->getRawLocalBuffer();
                         const std::vector<OutOfBlockInteraction>* outsideInteractions = &(*currentInteractions).interactions;
 
+#ifdef OPENMP_SUPPORT_COMMUTE
+                        #pragma omp task default(none) firstprivate(currentCells, cellPoles, cellLocals, outsideInteractions, cellsOther, cellOtherPoles, cellOtherLocals, idxLevel) depend(commute: cellLocals[0], cellOtherLocals[0]) depend(in: cellPoles[0], cellOtherPoles[0])
+#else
                         #pragma omp task default(none) firstprivate(currentCells, cellPoles, cellLocals, outsideInteractions, cellsOther, cellOtherPoles, cellOtherLocals, idxLevel) depend(inout: cellLocals[0], cellOtherLocals[0]) depend(in: cellPoles[0], cellOtherPoles[0])
+#endif
                         {
                             KernelClass*const kernel = kernels[omp_get_thread_num()];
                             const CellClass* interactions[343];
@@ -546,7 +554,11 @@ protected:
                     FAssertLF( nbSubCellGroups <= 9 );
                 }
 
+#ifdef OPENMP_SUPPORT_COMMUTE
+                #pragma omp task default(none) firstprivate(idxLevel, currentCells, cellLocals, subCellGroups, subCellLocalGroupsLocal, nbSubCellGroups) depend(commute: subCellLocalGroupsLocal[0][0], subCellLocalGroupsLocal[1][0], subCellLocalGroupsLocal[2][0], subCellLocalGroupsLocal[3][0], subCellLocalGroupsLocal[4][0], subCellLocalGroupsLocal[5][0], subCellLocalGroupsLocal[6][0], subCellLocalGroupsLocal[7][0], subCellLocalGroupsLocal[8][0]) depend(in: cellLocals[0])
+#else
                 #pragma omp task default(none) firstprivate(idxLevel, currentCells, cellLocals, subCellGroups, subCellLocalGroupsLocal, nbSubCellGroups) depend(inout: subCellLocalGroupsLocal[0][0], subCellLocalGroupsLocal[1][0], subCellLocalGroupsLocal[2][0], subCellLocalGroupsLocal[3][0], subCellLocalGroupsLocal[4][0], subCellLocalGroupsLocal[5][0], subCellLocalGroupsLocal[6][0], subCellLocalGroupsLocal[7][0], subCellLocalGroupsLocal[8][0]) depend(in: cellLocals[0])
+#endif
                 {
                     const MortonIndex blockStartIdx = currentCells->getStartingIndex();
                     const MortonIndex blockEndIdx = currentCells->getEndingIndex();
@@ -600,7 +612,11 @@ protected:
                 ParticleGroupClass* containers = (*iterParticles);
                 unsigned char* containersDown = containers->getRawAttributesBuffer();
 
+#ifdef OPENMP_SUPPORT_COMMUTE
+                #pragma omp task default(none) firstprivate(containers, containersDown) depend(commute: containersDown[0])
+#else
                 #pragma omp task default(none) firstprivate(containers, containersDown) depend(inout: containersDown[0])
+#endif
                 {
                     const MortonIndex blockStartIdx = containers->getStartingIndex();
                     const MortonIndex blockEndIdx = containers->getEndingIndex();
@@ -657,7 +673,11 @@ protected:
                     unsigned char* containersOtherDown = containersOther->getRawAttributesBuffer();
                     const std::vector<OutOfBlockInteraction>* outsideInteractions = &(*currentInteractions).interactions;
 
+#ifdef OPENMP_SUPPORT_COMMUTE
+                    #pragma omp task default(none) firstprivate(containers, containersDown, containersOther, containersOtherDown, outsideInteractions) depend(commute: containersOtherDown[0], containersDown[0])
+#else
                     #pragma omp task default(none) firstprivate(containers, containersDown, containersOther, containersOtherDown, outsideInteractions) depend(inout: containersOtherDown[0], containersDown[0])
+#endif
                     {
                         KernelClass*const kernel = kernels[omp_get_thread_num()];
                         for(int outInterIdx = 0 ; outInterIdx < int(outsideInteractions->size()) ; ++outInterIdx){
@@ -702,7 +722,11 @@ protected:
             ParticleGroupClass* containers = tree->getParticleGroup(idxGroup);
             unsigned char* containersDown = containers->getRawAttributesBuffer();
 
+#ifdef OPENMP_SUPPORT_COMMUTE
+            #pragma omp task default(shared) firstprivate(leafCells, cellLocals, containers, containersDown) depend(commute: containersDown[0]) depend(in: cellLocals[0])
+#else
             #pragma omp task default(shared) firstprivate(leafCells, cellLocals, containers, containersDown) depend(inout: containersDown[0]) depend(in: cellLocals[0])
+#endif
             {
                 const MortonIndex blockStartIdx = leafCells->getStartingIndex();
                 const MortonIndex blockEndIdx = leafCells->getEndingIndex();
diff --git a/Src/ScalFmmConfig.h.cmake b/Src/ScalFmmConfig.h.cmake
index 7d6a7acc6f82f653485b597ac1b8dce2c359ab08..12870da7d83b9ca5ad36b0919fad7fc43230e87a 100644
--- a/Src/ScalFmmConfig.h.cmake
+++ b/Src/ScalFmmConfig.h.cmake
@@ -105,4 +105,10 @@ const std::string SCALFMMDataPath("@CMAKE_SOURCE_DIR@/Data/");
 const std::string SCALFMMCompileFlags("@SCALFMM_COMPILE_FLAGS@");
 const std::string SCALFMMCompileLibs("@SCALFMM_COMPILE_LIBS@");
 
+///////////////////////////////////////////////////////
+// To use commute for KSTAR OMP4
+///////////////////////////////////////////////////////
+
+#cmakedefine OPENMP_SUPPORT_COMMUTE
+
 #endif // CONFIG_H