Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

2727 conditional accesses #2780

Open
wants to merge 9 commits into
base: master
Choose a base branch
from
3 changes: 1 addition & 2 deletions src/psyclone/core/access_type.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,6 @@

'''This module implements the AccessType used throughout PSyclone.'''

from __future__ import print_function, absolute_import
from enum import Enum
from psyclone.configuration import Config

Expand Down Expand Up @@ -109,7 +108,7 @@ def all_read_accesses():
:rtype: List of py:class:`psyclone.core.access_type.AccessType`.
'''
return [AccessType.READ, AccessType.READWRITE, AccessType.INC,
AccessType.READINC]
AccessType.READINC] + AccessType.get_valid_reduction_modes()

@staticmethod
def get_valid_reduction_modes():
Expand Down
32 changes: 29 additions & 3 deletions src/psyclone/core/component_indices.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,9 +36,7 @@

'''This module provides a class to manage indices in variable accesses.'''

from __future__ import print_function, absolute_import


from psyclone.core.symbolic_maths import SymbolicMaths
from psyclone.errors import InternalError


Expand Down Expand Up @@ -190,6 +188,34 @@ def get_subscripts_of(self, set_of_vars):
indices.append(unique_vars)
return indices

# ------------------------------------------------------------------------
def equal(self, other):
'''Checks whether `self` has the same indices as `other`. It uses
symbolic maths to compare the indices.
returns: whether self has the same indices as other.
:rtype: bool
'''

# We need to make sure the sizes are identical, otherwise:
# 1.) the zip below will stop after the shortest number of elements,
# 2.) we wouldn't be able to distinguish between a%b(i) and a(i)%b

# Same number of components:
if len(self) != len(other):
return False
# Same number of dimensions for each component
for i in range(len(self)):
if len(self._component_indices[i]) != \
len(other.indices_lists[i]):
return False

# Now the number of indices are identical, compare the actual indices:
sym_maths = SymbolicMaths.get()
for i, j in zip(self.iterate(), other.iterate()):
if not sym_maths.equal(self[i], other[j]):
return False
return True


# ---------- Documentation utils -------------------------------------------- #
# The list of module members that we wish AutoAPI to generate
Expand Down
61 changes: 57 additions & 4 deletions src/psyclone/core/single_variable_access_info.py
Original file line number Diff line number Diff line change
Expand Up @@ -68,12 +68,16 @@ class AccessInfo():
:type component_indices: None, [], a list or a list of lists of \
:py:class:`psyclone.psyir.nodes.Node` objects, or an object of type \
:py:class:`psyclone.core.component_indices.ComponentIndices`
:param bool conditional: if the access is a conditional access.

'''
def __init__(self, access_type, location, node, component_indices=None):
def __init__(self, access_type, location, node, component_indices=None,
conditional=False):
# pylint: disable=too-many-arguments
self._location = location
self._access_type = access_type
self._node = node
self._conditional = conditional
if not isinstance(component_indices, ComponentIndices):
self.component_indices = ComponentIndices(component_indices)
else:
Expand All @@ -82,7 +86,8 @@ def __init__(self, access_type, location, node, component_indices=None):
def __str__(self):
'''Returns a string representation showing the access mode
and location, e.g.: WRITE(5).'''
return f"{self._access_type}({self._location})"
return (f"{'%' if self._conditional else ''}"
f"{self._access_type}({self._location})")

def change_read_to_write(self):
'''This changes the access mode from READ to WRITE.
Expand Down Expand Up @@ -166,6 +171,36 @@ def node(self):
:rtype: :py:class:`psyclone.psyir.nodes.Node` '''
return self._node

@property
def is_read(self):
''':returns: whether this access includes a read access
(e.g. a READWRITE would also be a read access).
:rtype: bool
'''
return self._access_type in AccessType.all_read_accesses()

@property
def is_written(self):
''':returns: whether this access includes a write access
(e.g. a READWRITE would also be a write access).
:rtype: bool
'''
return self._access_type in AccessType.all_write_accesses()

@property
def conditional(self):
''':returns: whether the access is conditional.
:rtype: bool
'''
return self._conditional

@conditional.setter
def conditional(self, conditional):
'''Sets whether this access is conditional.
:param bool conditional: whether this access is conditional or not.
'''
self._conditional = conditional


# =============================================================================
class SingleVariableAccessInfo():
Expand Down Expand Up @@ -216,6 +251,22 @@ def is_written(self):
AccessType.all_write_accesses()
for access_info in self._accesses)

def is_conditional_read(self):
''':returns: if all read accesses to this variable are conditional,
meaning that this variable is read conditional
:rtype: bool
'''
return all(access_read.conditional
for access_read in self.all_read_accesses)

def is_conditional_write(self):
''':returns: if all write accesses to this variable are conditional,
meaning that this variable is written conditional
:rtype: bool
'''
return all(access_written.conditional
for access_written in self.all_write_accesses)

def is_written_first(self):
''':returns: True if this variable is written in the first access \
(which indicates that this variable is not an input variable \
Expand Down Expand Up @@ -286,7 +337,8 @@ def all_write_accesses(self):
if access.access_type in AccessType.all_write_accesses()]

def add_access_with_location(self, access_type, location, node,
component_indices):
component_indices, conditional=False):
# pylint: disable=too-many-arguments
'''Adds access information to this variable.

:param access_type: the type of access (READ, WRITE, ....)
Expand All @@ -300,9 +352,10 @@ def add_access_with_location(self, access_type, location, node,
access.
:type component_indices: \
:py:class:`psyclone.core.component_indices.ComponentIndices`
:param bool conditional: if the access is conditional
'''
self._accesses.append(AccessInfo(access_type, location, node,
component_indices))
component_indices, conditional))

def change_read_to_write(self):
'''This function is only used when analysing an assignment statement.
Expand Down
Loading
Loading