text:
import re
from datetime import date, datetime

from trac.attachment import Attachment
from trac.core import TracError
from trac.db.util import with_transaction
from trac.resource import Resource, ResourceNotFound
from trac.ticket.api import TicketSystem
from trac.util import embedded_numbers, partition
from trac.util.text import empty
from trac.util.datefmt import utc, utcmax, to_timestamp
from trac.util.translation import _

__all__ = ['Ticket', 'Type', 'Status', 'Resolution', 'Priority', 'Severity',
           'Component', 'Milestone', 'Version', 'group_milestones']

class Ticket(object):

    # Fields that must not be modified directly by the user
    protected_fields = ('resolution', 'status', 'time', 'changetime')

    @staticmethod
    def id_is_valid(num):
        return 0 < int(num) <= 1L << 31

    # 0.11 compatibility
    time_created = property(lambda self: self.values.get('time'))
    time_changed = property(lambda self: self.values.get('changetime'))

    def __init__(self, env, tkt_id=None, db=None, version=None):
        self.env = env
        if tkt_id is not None:
            tkt_id = int(tkt_id)
        self.resource = Resource('ticket', tkt_id, version)
        self.fields = TicketSystem(self.env).get_ticket_fields()
        self.time_fields = [f['name'] for f in self.fields
                            if f['type'] == 'time']
        self.values = {}
        if tkt_id is not None:
            self._fetch_ticket(tkt_id, db)
        else:
            self._init_defaults(db)
            self.id = None
        self._old = {}

    def _get_db(self, db):
        return db or self.env.get_db_cnx()

    exists = property(fget=lambda self: self.id is not None)

    def _init_defaults(self, db=None):
        for field in self.fields:
            default = None
            if field['name'] in self.protected_fields:
                # Ignore for new - only change through workflow
                pass
            elif not field.get('custom'):
                default = self.env.config.get('ticket',
                                              'default_' + field['name'])
            else:
                default = field.get('value')
                options = field.get('options')
                if default and options and default not in options:
                    try:
                        default = options[int(default)]
                    except (ValueError, IndexError):
                        self.env.log.warning('Invalid default value "%s" '
                                             'for custom field "%s"'
                                             % (default, field['name']))
            if default:
                self.values.setdefault(field['name'], default)

    def _fetch_ticket(self, tkt_id, db=None):
        row = None
        if self.id_is_valid(tkt_id):
            db = self._get_db(db)

            # Fetch the standard ticket fields
            std_fields = [f['name'] for f in self.fields if not f.get('custom')]
            cursor = db.cursor()
            cursor.execute("SELECT %s FROM ticket WHERE id=%%s"
                           % ','.join(std_fields), (tkt_id,))
            row = cursor.fetchone()
        if not row:
            raise ResourceNotFound(_('Ticket %(id)s does not exist.',
                                     id=tkt_id), _('Invalid ticket number'))

        self.id = tkt_id
        for i, field in enumerate(std_fields):
            value = row[i]
            if field in self.time_fields:
                self.values[field] = datetime.fromtimestamp(value or 0, utc)
            elif value is None:
                self.values[field] = empty
            else:
                self.values[field] = value

        # Fetch custom fields if available
        custom_fields = [f['name'] for f in self.fields if f.get('custom')]
        cursor.execute("SELECT name,value FROM ticket_custom WHERE ticket=%s",
                       (tkt_id,))
        for name, value in cursor:
            if name in custom_fields:
                if value is None:
                    self.values[name] = empty
                else:
                    self.values[name] = value

    def __getitem__(self, name):
        return self.values.get(name)

    def __setitem__(self, name, value):
        """Log ticket modifications so the table ticket_change can be updated"""
        if name in self.values and self.values[name] == value:
            return
        if name not in self._old: # Changed field
            self._old[name] = self.values.get(name)
        elif self._old[name] == value: # Change of field reverted
            del self._old[name]
        if value:
            if isinstance(value, list):
                raise TracError(_("Multi-values fields not supported yet"))
            field = [field for field in self.fields if field['name'] == name]
            if field and field[0].get('type') != 'textarea':
                value = value.strip()
        self.values[name] = value

    def get_value_or_default(self, name):
        """Return the value of a field or the default value if it is
        undefined"""
        try:
            value = self.values[name]
            if value is not empty:
                return value
            field = [field for field in self.fields if field['name'] == name]
            if field:
                return field[0].get('value', '')
        except KeyError:
            pass

    def populate(self, values):
        """Populate the ticket with 'suitable' values from a dictionary"""
        field_names = [f['name'] for f in self.fields]
        for name in [name for name in values.keys() if name in field_names]:
            self[name] = values.get(name, '')

        # We have to do an extra trick to catch unchecked checkboxes
        for name in [name for name in values.keys() if name[9:] in field_names
                     and name.startswith('checkbox_')]:
            if name[9:] not in values:
                self[name[9:]] = '0'

    def insert(self, when=None, db=None):
        """Add ticket to database"""
        assert not self.exists, 'Cannot insert an existing ticket'

        # Add a timestamp
        if when is None:
            when = datetime.now(utc)
        self.values['time'] = self.values['changetime'] = when

        # The owner field defaults to the component owner
        if self.values.get('component') and not self.values.get('owner'):
            try:
                component = Component(self.env, self['component'], db=db)
                if component.owner:
                    self['owner'] = component.owner
            except ResourceNotFound:
                # No such component exists
                pass

        # Perform type conversions
        values = dict(self.values)
        for field in self.time_fields:
            if field in values:
                values[field] = to_timestamp(values[field])

        # Insert ticket record
        std_fields = []
        custom_fields = []
        for f in self.fields:
            fname = f['name']
            if fname in self.values:
                if f.get('custom'):
                    custom_fields.append(fname)
                else:
                    std_fields.append(fname)

        @with_transaction(self.env, db)
        def do_insert(db):
            cursor = db.cursor()
            cursor.execute("INSERT INTO ticket (%s) VALUES (%s)"
                           % (','.join(std_fields),
                              ','.join(['%s'] * len(std_fields))),
                           [values[name] for name in std_fields])
            self.id = db.get_last_id(cursor, 'ticket')

            # Insert custom fields
            if custom_fields:
                cursor.executemany("INSERT INTO ticket_custom "
                                   "(ticket,name,value) VALUES (%s,%s,%s)",
                                   [(self.id, name, self[name])
                                    for name in custom_fields])

        self.resource = self.resource(id=self.id)
        self._old = {}

        for listener in TicketSystem(self.env).change_listeners:
            listener.ticket_created(self)

        return self.id

    def save_changes(self, author, comment, when=None, db=None, cnum=''):
        """
        Store ticket changes in the database. The ticket must already exist in
        the database.  Returns False if there were no changes to save, True
        otherwise.
        """
        assert self.exists, 'Cannot update a new ticket'

        if not self._old and not comment:
            return False # Not modified

        if when is None:
            when = datetime.now(utc)
        when_ts = to_timestamp(when)

        if 'component' in self.values:
            # If the component is changed on a 'new' ticket
            # then owner field is updated accordingly. (#623).
            if self.values.get('status') == 'new' \
                    and 'component' in self._old \
                    and 'owner' not in self._old:
                try:
                    old_comp = Component(self.env, self._old['component'])
                    old_owner = old_comp.owner or ''
                    current_owner = self.values.get('owner') or ''
                    if old_owner == current_owner:
                        new_comp = Component(self.env, self['component'])
                        if new_comp.owner:
                            self['owner'] = new_comp.owner
                except TracError:
                    # If the old component has been removed from the database we
                    # just leave the owner as is.
                    pass

        # Fix up cc list separators and remove duplicates
        if 'cc' in self.values:
            cclist = []
            for cc in re.split(r'[;,\s]+', self.values['cc']):
                if cc not in cclist:
                    cclist.append(cc)
            self.values['cc'] = ', '.join(cclist)

        @with_transaction(self.env, db)
        def do_save(db):
            cursor = db.cursor()

            # find cnum if it isn't provided
            comment_num = cnum
            if not comment_num:
                num = 0
                cursor.execute("""
                    SELECT DISTINCT tc1.time,COALESCE(tc2.oldvalue,'')
                    FROM ticket_change AS tc1
                      LEFT OUTER JOIN
                        (SELECT time,oldvalue FROM ticket_change
                         WHERE field='comment') AS tc2
                      ON (tc1.time = tc2.time)
                    WHERE ticket=%s ORDER BY tc1.time DESC
                    """, (self.id,))
                for ts, old in cursor:
                    # Use oldvalue if available, else count edits
                    try:
                        num += int(old.rsplit('.', 1)[-1])
                        break
                    except ValueError:
                        num += 1
                comment_num = str(num + 1)

            # store fields
            custom_fields = [f['name'] for f in self.fields if f.get('custom')]

            for name in self._old.keys():
                if name in custom_fields:
                    cursor.execute("""
                        SELECT * FROM ticket_custom
                        WHERE ticket=%s and name=%s
                        """, (self.id, name))
                    if cursor.fetchone():
                        cursor.execute("""
                            UPDATE ticket_custom SET value=%s
                            WHERE ticket=%s AND name=%s
                            """, (self[name], self.id, name))
                    else:
                        cursor.execute("""
                            INSERT INTO ticket_custom (ticket,name,value)
                            VALUES(%s,%s,%s)
                            """, (self.id, name, self[name]))
                else:
                    cursor.execute("UPDATE ticket SET %s=%%s WHERE id=%%s"
                                   % name, (self[name], self.id))
                cursor.execute("""
                    INSERT INTO ticket_change
                        (ticket,time,author,field,oldvalue,newvalue)
                    VALUES (%s, %s, %s, %s, %s, %s)
                    """, (self.id, when_ts, author, name, self._old[name],
                          self[name]))

            # always save comment, even if empty
            # (numbering support for timeline)
            cursor.execute("""
                INSERT INTO ticket_change
                    (ticket,time,author,field,oldvalue,newvalue)
                VALUES (%s,%s,%s,'comment',%s,%s)
                """, (self.id, when_ts, author, comment_num, comment))

            cursor.execute("UPDATE ticket SET changetime=%s WHERE id=%s",
                           (when_ts, self.id))

        old_values = self._old
        self._old = {}
        self.values['changetime'] = when

        for listener in TicketSystem(self.env).change_listeners:
            listener.ticket_changed(self, comment, author, old_values)
        return True

    def get_changelog(self, when=None, db=None):
        """Return the changelog as a list of tuples of the form
        (time, author, field, oldvalue, newvalue, permanent).

        While the other tuple elements are quite self-explanatory,
        the `permanent` flag is used to distinguish collateral changes
        that are not yet immutable (like attachments, currently).
        """
        db = self._get_db(db)
        cursor = db.cursor()
        sid = str(self.id)
        when_ts = when and to_timestamp(when) or 0
        if when_ts:
            cursor.execute("SELECT time,author,field,oldvalue,newvalue,"
                           "1 AS permanent FROM ticket_change "
                           "WHERE ticket=%s AND time=%s "
                           "UNION "
                           "SELECT time,author,'attachment',null,filename,"
                           "0 AS permanent FROM attachment "
                           "WHERE id=%s AND time=%s "
                           "UNION "
                           "SELECT time,author,'comment',null,description,"
                           "0 AS permanent FROM attachment "
                           "WHERE id=%s AND time=%s "
                           "ORDER BY time,permanent,author",
                           (self.id, when_ts, sid, when_ts, sid, when_ts))
        else:
            cursor.execute("SELECT time,author,field,oldvalue,newvalue,"
                           "1 AS permanent FROM ticket_change WHERE ticket=%s "
                           "UNION "
                           "SELECT time,author,'attachment',null,filename,"
                           "0 AS permanent FROM attachment WHERE id=%s "
                           "UNION "
                           "SELECT time,author,'comment',null,description,"
                           "0 AS permanent FROM attachment WHERE id=%s "
                           "ORDER BY time,permanent,author",
                           (self.id, sid, sid))
        log = []
        for t, author, field, oldvalue, newvalue, permanent in cursor:
            log.append((datetime.fromtimestamp(int(t), utc), author, field,
                       oldvalue or '', newvalue or '', permanent))
        return log

    def delete(self, db=None):
        @with_transaction(self.env, db)
        def do_delete(db):
            Attachment.delete_all(self.env, 'ticket', self.id, db)
            cursor = db.cursor()
            cursor.execute("DELETE FROM ticket WHERE id=%s", (self.id,))
            cursor.execute("DELETE FROM ticket_change WHERE ticket=%s",
                           (self.id,))
            cursor.execute("DELETE FROM ticket_custom WHERE ticket=%s",
                           (self.id,))

        for listener in TicketSystem(self.env).change_listeners:
            listener.ticket_deleted(self)

    def get_change(self, cnum, db=None):
        """Return a ticket change by its number."""
        db = self._get_db(db)
        cursor = db.cursor()
        row = self._find_comment(cnum, db)
        if row:
            ts, author, comment = row
            cursor.execute("SELECT field,author,oldvalue,newvalue "
                           "FROM ticket_change "
                           "WHERE ticket=%s AND time=%s",
                           (self.id, ts))
            fields = {}
            change = {'date': datetime.fromtimestamp(int(ts), utc),
                      'author': author, 'fields': fields}
            for field, author, old, new in cursor:
                fields[field] = {'author': author, 'old': old, 'new': new}
            return change

    def modify_comment(self, cdate, author, comment, when=None, db=None):
        """Modify a ticket comment specified by its date, while keeping a
        history of edits.
        """
        ts = to_timestamp(cdate)
        if when is None:
            when = datetime.now(utc)
        when_ts = to_timestamp(when)

        @with_transaction(self.env, db)
        def do_save(db):
            cursor = db.cursor()
            # Find the current value of the comment
            cursor.execute("SELECT newvalue FROM ticket_change "
                           "WHERE ticket=%s AND time=%s AND field='comment'",
                           (self.id, ts))
            old_comment = False
            for old_comment, in cursor:
                break
            if comment == (old_comment or ''):
                return

            # Comment history is stored in fields named "_comment%d"
            # Find the next edit number
            cursor.execute("SELECT field FROM ticket_change "
                           "WHERE ticket=%%s AND time=%%s AND field %s"
                           % db.like(),
                           (self.id, ts, db.like_escape('_comment') + '%'))
            fields = list(cursor)
            rev = fields and max(int(field[8:]) for field, in fields) + 1 or 0
            cursor.execute("INSERT INTO ticket_change "
                           "(ticket,time,author,field,oldvalue,newvalue) "
                           "VALUES (%s,%s,%s,%s,%s,%s)",
                           (self.id, ts, author, '_comment%d' % rev,
                            old_comment or '', str(when_ts)))
            if old_comment is False:
                # There was no comment field, add one, find the original author
                # in one of the other changed fields
                cursor.execute("SELECT author FROM ticket_change "
                               "WHERE ticket=%%s AND time=%%s AND NOT field %s"
                               " LIMIT 1" % db.like(),
                               (self.id, ts, db.like_escape('_') + '%'))
                old_author = None
                for old_author, in cursor:
                    break
                cursor.execute("INSERT INTO ticket_change "
                               " (ticket,time,author,field,oldvalue,newvalue) "
                               "VALUES (%s,%s,%s,'comment','',%s)",
                               (self.id, ts, old_author, comment))
            else:
                cursor.execute("UPDATE ticket_change SET newvalue=%s "
                               "WHERE ticket=%s AND time=%s AND "
                               "field='comment'",
                               (comment, self.id, ts))

    def get_comment_history(self, cnum, db=None):
        db = self._get_db(db)
        history = []
        cursor = db.cursor()
        row = self._find_comment(cnum, db)
        if row:
            ts0, author0, last_comment = row
            # Get all fields of the form "_comment%d"
            cursor.execute("SELECT field,author,oldvalue,newvalue "
                           "FROM ticket_change "
                           "WHERE ticket=%%s AND time=%%s AND field %s"
                           % db.like(),
                           (self.id, ts0, db.like_escape('_comment') + '%'))
            rows = sorted((int(field[8:]), author, old, new)
                          for field, author, old, new in cursor)
            for rev, author, comment, ts in rows:
                history.append((rev, datetime.fromtimestamp(int(ts0), utc),
                                author0, comment))
                ts0, author0 = ts, author
            history.sort()
            rev = history and (history[-1][0] + 1) or 0
            history.append((rev, datetime.fromtimestamp(int(ts0), utc),
                            author0, last_comment))
        return history

    def _find_comment(self, cnum, db):
        """Find a comment by its number."""
        scnum = str(cnum)
        cursor = db.cursor()
        cursor.execute("SELECT time,author,newvalue FROM ticket_change "
                       "WHERE ticket=%%s AND field='comment' "
                       "  AND (oldvalue=%%s OR oldvalue %s)"
                       % db.like(),
                       (self.id, scnum, '%' + db.like_escape('.' + scnum)))
        for row in cursor:
            return row

        # Fallback when comment number is not available in oldvalue
        num = 0
        cursor.execute("SELECT DISTINCT tc1.time,COALESCE(tc2.oldvalue,''), "
                       "                tc2.author,COALESCE(tc2.newvalue,'') "
                       "FROM ticket_change AS tc1 "
                       " LEFT OUTER JOIN "
                       "   (SELECT time,author,oldvalue,newvalue "
                       "    FROM ticket_change "
                       "    WHERE field='comment') AS tc2 "
                       " ON (tc1.time = tc2.time) "
                       "WHERE ticket=%s "
                       "ORDER BY tc1.time",
                       (self.id,))
        for ts, old, author, comment in cursor:
            # Use oldvalue if available, else count edits
            try:
                num = int(old.rsplit('.', 1)[-1])
            except ValueError:
                num += 1
            if num == cnum:
                break
        else:
            return

        # Find author if NULL
        if author is None:
            cursor.execute("SELECT author FROM ticket_change "
                           "WHERE ticket=%%s AND time=%%s "
                           "      AND NOT field %s "
                           "LIMIT 1" % db.like(),
                           (self.id, ts, db.like_escape('_') + '%'))
            for author, in cursor:
                break
        return (ts, author, comment)

def simplify_whitespace(name):
    """Strip spaces and remove duplicate spaces within names"""
    if name:
        return ' '.join(name.split())
    return name

class AbstractEnum(object):
    type = None
    ticket_col = None

    def __init__(self, env, name=None, db=None):
        if not self.ticket_col:
            self.ticket_col = self.type
        self.env = env
        name = simplify_whitespace(name)
        if name:
            if not db:
                db = self.env.get_db_cnx()
            cursor = db.cursor()
            cursor.execute("SELECT value FROM enum WHERE type=%s AND name=%s",
                           (self.type, name))
            row = cursor.fetchone()
            if not row:
                raise ResourceNotFound(_('%(type)s %(name)s does not exist.',
                                         type=self.type, name=name))
            self.value = self._old_value = row[0]
            self.name = self._old_name = name
        else:
            self.value = self._old_value = None
            self.name = self._old_name = None

    exists = property(fget=lambda self: self._old_value is not None)

    def delete(self, db=None):
        assert self.exists, 'Cannot delete non-existent %s' % self.type

        @with_transaction(self.env, db)
        def do_delete(db):
            cursor = db.cursor()
            self.env.log.info('Deleting %s %s' % (self.type, self.name))
            cursor.execute("DELETE FROM enum WHERE type=%s AND value=%s",
                           (self.type, self._old_value))
            # Re-order any enums that have higher value than deleted (close gap)
            for enum in list(self.select(self.env, db)):
                try:
                    if int(enum.value) > int(self._old_value):
                        enum.value = unicode(int(enum.value) - 1)
                        enum.update(db=db)
                except ValueError:
                    pass # Ignore cast error for this non-essential operation
            TicketSystem(self.env).reset_ticket_fields(db)
        self.value = self._old_value = None
        self.name = self._old_name = None

    def insert(self, db=None):
        assert not self.exists, 'Cannot insert existing %s' % self.type
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid %(type)s name.', type=self.type))

        @with_transaction(self.env, db)
        def do_insert(db):
            cursor = db.cursor()
            self.env.log.debug("Creating new %s '%s'" % (self.type, self.name))
            if not self.value:
                cursor.execute(("SELECT COALESCE(MAX(%s),0) FROM enum "
                                "WHERE type=%%s") % db.cast('value', 'int'),
                               (self.type,))
                self.value = int(float(cursor.fetchone()[0])) + 1
            cursor.execute("INSERT INTO enum (type,name,value) "
                           "VALUES (%s,%s,%s)",
                           (self.type, self.name, self.value))
            TicketSystem(self.env).reset_ticket_fields(db)

        self._old_name = self.name
        self._old_value = self.value

    def update(self, db=None):
        assert self.exists, 'Cannot update non-existent %s' % self.type
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid %(type)s name.', type=self.type))

        @with_transaction(self.env, db)
        def do_update(db):
            cursor = db.cursor()
            self.env.log.info('Updating %s "%s"' % (self.type, self.name))
            cursor.execute("UPDATE enum SET name=%s,value=%s "
                           "WHERE type=%s AND name=%s",
                           (self.name, self.value, self.type, self._old_name))
            if self.name != self._old_name:
                # Update tickets
                cursor.execute("UPDATE ticket SET %s=%%s WHERE %s=%%s" %
                               (self.ticket_col, self.ticket_col),
                               (self.name, self._old_name))
            TicketSystem(self.env).reset_ticket_fields(db)

        self._old_name = self.name
        self._old_value = self.value

    @classmethod
    def select(cls, env, db=None):
        if not db:
            db = env.get_db_cnx()
        cursor = db.cursor()
        cursor.execute("SELECT name,value FROM enum WHERE type=%s "
                       "ORDER BY " + db.cast('value', 'int'),
                       (cls.type,))
        for name, value in cursor:
            obj = cls(env)
            obj.name = obj._old_name = name
            obj.value = obj._old_value = value
            yield obj

class Type(AbstractEnum):
    type = 'ticket_type'
    ticket_col = 'type'

class Status(object):
    def __init__(self, env):
        self.env = env

    @classmethod
    def select(cls, env, db=None):
        for state in TicketSystem(env).get_all_status():
            status = cls(env)
            status.name = state
            yield status

class Resolution(AbstractEnum):
    type = 'resolution'

class Priority(AbstractEnum):
    type = 'priority'

class Severity(AbstractEnum):
    type = 'severity'

class Component(object):

    def __init__(self, env, name=None, db=None):
        self.env = env
        name = simplify_whitespace(name)
        if name:
            if not db:
                db = self.env.get_db_cnx()
            cursor = db.cursor()
            cursor.execute("SELECT owner,description FROM component "
                           "WHERE name=%s", (name,))
            row = cursor.fetchone()
            if not row:
                raise ResourceNotFound(_('Component %(name)s does not exist.',
                                         name=name))
            self.name = self._old_name = name
            self.owner = row[0] or None
            self.description = row[1] or ''
        else:
            self.name = self._old_name = None
            self.owner = None
            self.description = None

    exists = property(fget=lambda self: self._old_name is not None)

    def delete(self, db=None):
        assert self.exists, 'Cannot delete non-existent component'

        @with_transaction(self.env, db)
        def do_delete(db):
            cursor = db.cursor()
            self.env.log.info('Deleting component %s' % self.name)
            cursor.execute("DELETE FROM component WHERE name=%s", (self.name,))
            self.name = self._old_name = None
            TicketSystem(self.env).reset_ticket_fields(db)

    def insert(self, db=None):
        assert not self.exists, 'Cannot insert existing component'
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid component name.'))

        @with_transaction(self.env, db)
        def do_insert(db):
            cursor = db.cursor()
            self.env.log.debug("Creating new component '%s'" % self.name)
            cursor.execute("INSERT INTO component (name,owner,description) "
                           "VALUES (%s,%s,%s)",
                           (self.name, self.owner, self.description))
            self._old_name = self.name
            TicketSystem(self.env).reset_ticket_fields(db)

    def update(self, db=None):
        assert self.exists, 'Cannot update non-existent component'
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid component name.'))

        @with_transaction(self.env, db)
        def do_update(db):
            cursor = db.cursor()
            self.env.log.info('Updating component "%s"' % self.name)
            cursor.execute("UPDATE component SET name=%s,owner=%s,"
                           "description=%s WHERE name=%s",
                           (self.name, self.owner, self.description,
                            self._old_name))
            if self.name != self._old_name:
                # Update tickets
                cursor.execute("UPDATE ticket SET component=%s "
                               "WHERE component=%s",
                               (self.name, self._old_name))
                self._old_name = self.name
            TicketSystem(self.env).reset_ticket_fields(db)

    @classmethod
    def select(cls, env, db=None):
        if not db:
            db = env.get_db_cnx()
        cursor = db.cursor()
        cursor.execute("SELECT name,owner,description FROM component "
                       "ORDER BY name")
        for name, owner, description in cursor:
            component = cls(env)
            component.name = component._old_name = name
            component.owner = owner or None
            component.description = description or ''
            yield component

class Milestone(object):

    def __init__(self, env, name=None, db=None):
        self.env = env
        name = simplify_whitespace(name)
        if name:
            self._fetch(name, db)
        else:
            self.name = None
            self.due = self.completed = None
            self.description = ''
            self._to_old()

    def _get_resource(self):
        return Resource('milestone', self.name) ### .version !!!
    resource = property(_get_resource)

    def _fetch(self, name, db=None):
        if not db:
            db = self.env.get_db_cnx()
        cursor = db.cursor()
        cursor.execute("SELECT name,due,completed,description "
                       "FROM milestone WHERE name=%s", (name,))
        row = cursor.fetchone()
        if not row:
            raise ResourceNotFound(_('Milestone %(name)s does not exist.',
                                   name=name), _('Invalid milestone name'))
        self._from_database(row)

    exists = property(fget=lambda self: self._old['name'] is not None)
    is_completed = property(fget=lambda self: self.completed is not None)
    is_late = property(fget=lambda self: self.due and \
                                         self.due.date() < date.today())

    def _from_database(self, row):
        name, due, completed, description = row
        self.name = name
        self.due = due and datetime.fromtimestamp(int(due), utc) or None
        self.completed = completed and \
                         datetime.fromtimestamp(int(completed), utc) or None
        self.description = description or ''
        self._to_old()

    def _to_old(self):
        self._old = {'name': self.name, 'due': self.due,
                     'completed': self.completed,
                     'description': self.description}

    def delete(self, retarget_to=None, author=None, db=None):
        @with_transaction(self.env, db)
        def do_delete(db):
            cursor = db.cursor()
            self.env.log.info('Deleting milestone %s' % self.name)
            cursor.execute("DELETE FROM milestone WHERE name=%s", (self.name,))

            # Retarget/reset tickets associated with this milestone
            now = datetime.now(utc)
            cursor.execute("SELECT id FROM ticket WHERE milestone=%s",
                           (self.name,))
            tkt_ids = [int(row[0]) for row in cursor]
            for tkt_id in tkt_ids:
                ticket = Ticket(self.env, tkt_id, db)
                ticket['milestone'] = retarget_to
                ticket.save_changes(author, 'Milestone %s deleted' % self.name,
                                    now, db=db)
            self._old['name'] = None
            TicketSystem(self.env).reset_ticket_fields(db)

        for listener in TicketSystem(self.env).milestone_change_listeners:
            listener.milestone_deleted(self)

    def insert(self, db=None):
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid milestone name.'))

        @with_transaction(self.env, db)
        def do_insert(db):
            cursor = db.cursor()
            self.env.log.debug("Creating new milestone '%s'" % self.name)
            cursor.execute("INSERT INTO milestone "
                           "(name,due,completed,description) "
                           "VALUES (%s,%s,%s,%s)",
                           (self.name, to_timestamp(self.due),
                            to_timestamp(self.completed), self.description))
            self._to_old()
            TicketSystem(self.env).reset_ticket_fields(db)

        for listener in TicketSystem(self.env).milestone_change_listeners:
            listener.milestone_created(self)

    def update(self, db=None):
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid milestone name.'))

        @with_transaction(self.env, db)
        def do_insert(db):
            cursor = db.cursor()
            self.env.log.info('Updating milestone "%s"' % self.name)
            cursor.execute("UPDATE milestone SET name=%s,due=%s,"
                           "completed=%s,description=%s WHERE name=%s",
                           (self.name, to_timestamp(self.due),
                            to_timestamp(self.completed),
                            self.description, self._old['name']))
            self.env.log.info('Updating milestone field of all tickets '
                              'associated with milestone "%s"' % self.name)
            cursor.execute("UPDATE ticket SET milestone=%s WHERE milestone=%s",
                           (self.name, self._old['name']))
            TicketSystem(self.env).reset_ticket_fields(db)

        old_values = dict((k, v) for k, v in self._old.iteritems()
                          if getattr(self, k) != v)
        self._to_old()
        for listener in TicketSystem(self.env).milestone_change_listeners:
            listener.milestone_changed(self, old_values)

    @classmethod
    def select(cls, env, include_completed=True, db=None):
        if not db:
            db = env.get_db_cnx()
        sql = "SELECT name,due,completed,description FROM milestone "
        if not include_completed:
            sql += "WHERE COALESCE(completed,0)=0 "
        cursor = db.cursor()
        cursor.execute(sql)
        milestones = []
        for row in cursor:
            milestone = Milestone(env)
            milestone._from_database(row)
            milestones.append(milestone)
        def milestone_order(m):
            return (m.completed or utcmax,
                    m.due or utcmax,
                    embedded_numbers(m.name))
        return sorted(milestones, key=milestone_order)

def group_milestones(milestones, include_completed):
    """Group milestones into "open with due date", "open with no due date",
    and possibly "completed". Return a list of (label, milestones) tuples."""
    def category(m):
        return m.is_completed and 1 or m.due and 2 or 3
    open_due_milestones, open_not_due_milestones, \
        closed_milestones = partition([(m, category(m))
            for m in milestones], (2, 3, 1))
    groups = [
        (_('Open (by due date)'), open_due_milestones),
        (_('Open (no due date)'), open_not_due_milestones),
    ]
    if include_completed:
        groups.append((_('Closed'), closed_milestones))
    return groups

class Version(object):

    def __init__(self, env, name=None, db=None):
        self.env = env
        name = simplify_whitespace(name)
        if name:
            if not db:
                db = self.env.get_db_cnx()
            cursor = db.cursor()
            cursor.execute("SELECT time,description FROM version "
                           "WHERE name=%s", (name,))
            row = cursor.fetchone()
            if not row:
                raise ResourceNotFound(_('Version %(name)s does not exist.',
                                         name=name))
            self.name = self._old_name = name
            self.time = row[0] and datetime.fromtimestamp(int(row[0]), utc) \
                            or None
            self.description = row[1] or ''
        else:
            self.name = self._old_name = None
            self.time = None
            self.description = None

    exists = property(fget=lambda self: self._old_name is not None)

    def delete(self, db=None):
        assert self.exists, 'Cannot delete non-existent version'

        @with_transaction(self.env, db)
        def do_delete(db):
            cursor = db.cursor()
            self.env.log.info('Deleting version %s' % self.name)
            cursor.execute("DELETE FROM version WHERE name=%s", (self.name,))
            self.name = self._old_name = None
            TicketSystem(self.env).reset_ticket_fields(db)

    def insert(self, db=None):
        assert not self.exists, 'Cannot insert existing version'
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid version name.'))

        @with_transaction(self.env, db)
        def do_insert(db):
            cursor = db.cursor()
            self.env.log.debug("Creating new version '%s'" % self.name)
            cursor.execute("INSERT INTO version (name,time,description) "
                           "VALUES (%s,%s,%s)",
                           (self.name, to_timestamp(self.time),
                            self.description))
            self._old_name = self.name
            TicketSystem(self.env).reset_ticket_fields(db)

    def update(self, db=None):
        assert self.exists, 'Cannot update non-existent version'
        self.name = simplify_whitespace(self.name)
        if not self.name:
            raise TracError(_('Invalid version name.'))

        @with_transaction(self.env, db)
        def do_update(db):
            cursor = db.cursor()
            self.env.log.info('Updating version "%s"' % self.name)
            cursor.execute("UPDATE version SET name=%s,time=%s,description=%s "
                           "WHERE name=%s",
                           (self.name, to_timestamp(self.time),
                            self.description, self._old_name))
            if self.name != self._old_name:
                # Update tickets
                cursor.execute("UPDATE ticket SET version=%s WHERE version=%s",
                               (self.name, self._old_name))
                self._old_name = self.name
            TicketSystem(self.env).reset_ticket_fields(db)

    @classmethod
    def select(cls, env, db=None):
        if not db:
            db = env.get_db_cnx()
        cursor = db.cursor()
        cursor.execute("SELECT name,time,description FROM version")
        versions = []
        for name, time, description in cursor:
            version = cls(env)
            version.name = version._old_name = name
            version.time = time and datetime.fromtimestamp(int(time), utc) \
                                or None
            version.description = description or ''
            versions.append(version)
        def version_order(v):
            return (v.time or utcmax, embedded_numbers(v.name))
        return sorted(versions, key=version_order, reverse=True)


text:
/**
 * Removes operations from the model if they require event streams.
 * Specifically looks at input and output shapes.
 * @param {Object} model - JSON parsed API model (*.normal.json)
 */
function removeEventStreamOperations(model) {
    var modifiedModel = false;
    // loop over all operations
    var operations = model.operations;
    var operationNames = Object.keys(operations);
    for (var i = 0; i < operationNames.length; i++) {
        var operationName = operationNames[i];
        var operation = operations[operationName];
        // check input and output shapes
        var inputShapeName = operation.input && operation.input.shape;
        var outputShapeName = operation.output && operation.output.shape;

        var requiresEventStream = false;
        if (inputShapeName && hasEventStream(model.shapes[inputShapeName], model)) {
            requiresEventStream = true;
        }

        if (requiresEventStream) {
            modifiedModel = true;
            // remove the operation from the model
            console.log('Removing ' + operationName + ' because it depends on event streams on input.');
            delete model.operations[operationName];
        }
    }
    return modifiedModel;
}

function hasEventStream(shape, model) {
    if (shape.eventstream) {
        return true;
    } else {
        // check each member shape
        var memberNames = Object.keys(shape.members);
        for (var i = 0; i < memberNames.length; i++) {
            var member = shape.members[memberNames[i]];
            if (member.eventstream) {
                return true;
            }
            var memberShape = model.shapes[member.shape];
            if (memberShape.eventstream) {
                return true;
            }
        }
    }
}

module.exports = {
    removeEventStreamOperations: removeEventStreamOperations
};

redpajama_set_name: RedPajamaGithub


text:
package com.skf.mokao.validator;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.skf.mokao.pojo.Proxyips;
import com.skf.mokao.commons.Config;
import com.skf.mokao.pojo.SpiderProxyips;
import com.skf.mokao.utils.SpiderUtil;
import org.jsoup.Connection;
import org.jsoup.Jsoup;

import javax.net.ssl.HttpsURLConnection;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.InetSocketAddress;
import java.net.Proxy;
import java.net.URL;
import java.util.*;

/**
 * Created by Administrator on 2017/8/29.
 * 检测数据库数据可用性
 * 代理可用:Score不变 代理已不可用:Score-1
 * Score为0则代表代理已失效--删除
 */

public class Validator {

    private List<Proxyips> proxies;

    public Validator(List<Proxyips> proxies) {
        this.proxies = proxies;
    }

    public List<Proxyips> getProxies() {

        return proxies;
    }

    public void setProxies(List<Proxyips> proxies) {
        this.proxies = proxies;
    }

    /**
     * 用来检测代理的类型,免费网站写的信息不靠谱,还是要自己检测代理的类型
     * type类型( 0: 高匿,1:匿名,2 透明),protocol(0: http, 1 https, 2 http/https),
     * protocol 支持网络类型 (0:HTTP 1:HTTPS 2:HTTP/HTTPS)
     * @param ip
     * @param port
     * @return
     */
    public static SpiderProxyips checkProxy(String ip, String port) {

        SpiderProxyips proxyips = null;
        double speed = 0;
        int type = -1;
        int protocol = -1;

        //只要代理IP和代理端口正确,此项不设置也可以
//        System.setProperty("http.maxRedirects", "50");
//        System.getProperties().setProperty("proxySet", "true");

        if (ip.replaceAll("[\\s\\u00A0\\u0020]+$", "").equals("")
                || port.replaceAll("[\\s\\u00A0\\u0020]+$", "").equals("")) {
            return null;
        }
        Map<String, Object> httpRes = checkHttpProxy(ip, port);
        Map<String, Object> httpsRes = checkHttpsProxy(ip, port);
        if ((int) httpRes.get("http") == 1 && (int) httpsRes.get("https") == 1) {
            type = (int) httpRes.get("type");
            speed = (double) httpRes.get("speed");
            protocol = 2; //HTTP&HTTPS
        } else if ((int) httpsRes.get("https") == 1) {
            type = (int) httpsRes.get("type");
            speed = (double) httpsRes.get("speed");
            protocol = 1; //HTTPS
        } else if ((int) httpRes.get("http") == 1) {
            type = (int) httpRes.get("type");
            speed = (double) httpRes.get("speed");
            protocol = 0; //HTTP
        }

        //过滤掉 :代理失败的、 速度太慢的、 透明的代理
        if (protocol != -1 && type != -1 && type != 2 && speed != 0 && speed < 10) {
            proxyips = new SpiderProxyips();
            proxyips.setIP(ip);
            proxyips.setPort(port);
            proxyips.setTypes(type);
            proxyips.setProtocol(protocol);
            proxyips.setSpeed(speed);
        }
        return proxyips;
    }

    private static Map<String, Object> checkHttpProxy(String ip, String port) {
        int type = -1;
        double speed = 0;
        InputStream is = null;
        BufferedReader buffer = null;
        StringBuffer bs = null;
        Map<String, Object> result = new HashMap<>();
        try {
            Proxy proxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress(ip, Integer.valueOf(port)));
            Date start = new Date();
            URL url = new URL(Config.TEST_HTTP_HEADER);
            HttpURLConnection urlcon = (HttpURLConnection) url.openConnection(proxy);
            // 设置通用的请求属性
            urlcon.setRequestProperty("user-agent",
                    SpiderUtil.USER_AGENTS.get((new Random().nextInt(SpiderUtil.USER_AGENTS.size()))));
            urlcon.setConnectTimeout(15000); //15s
            urlcon.setReadTimeout(15000);
            urlcon.setUseCaches(false);
            //获取连接
            urlcon.connect();
            is = urlcon.getInputStream();
            Date end = new Date();
            buffer = new BufferedReader(new InputStreamReader(is));
            bs = new StringBuffer();
            String l = null;
            while ((l = buffer.readLine()) != null) {
                bs.append(l);
            }
            if (urlcon.getResponseCode() == 200) {
                JSONObject json = JSON.parseObject(bs.toString());
                String ips = String.valueOf(json.get("origin"));
                Object proxy_connection = JSON.parseObject(json.get("headers").toString()).get("Proxy-Connection");
                if (ips.contains(","))
                    type = 2; // 透明
                else if (proxy_connection != null)
                    type = 1; //匿名
                else
                    type = 0; //高匿
                speed = (double) (end.getTime() - start.getTime()) / 1000.00;
            }
            result.put("http", 1);
            result.put("type", type);
            result.put("speed", speed);
            urlcon.disconnect();
            return result;
        } catch (Exception e) {
            result.put("http", 0);
            result.put("type", type);
            result.put("speed", speed);
            return result;
        }finally {
            try {
                if (is != null)
                    is.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
            try {
                if (buffer != null)
                    buffer.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    private static Map<String, Object> checkHttpsProxy(String ip, String port) {
        int type = -1;
        double speed = 0;
        InputStream is = null;
        BufferedReader buffer = null;
        StringBuffer bs = null;
        Map<String, Object> result = new HashMap<>();
        HttpsURLConnection urlcon = null;
        try {
            Proxy proxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress(ip, Integer.valueOf(port)));
            URL url = new URL(Config.TEST_HTTPS_HEADER);
            Date start = new Date();
            urlcon = (HttpsURLConnection) url.openConnection(proxy);
            // 设置通用的请求属性
            urlcon.setRequestProperty("user-agent",
                    SpiderUtil.USER_AGENTS.get((new Random().nextInt(SpiderUtil.USER_AGENTS.size()))));
            urlcon.setConnectTimeout(15000); //15s
            urlcon.setReadTimeout(15000);
            urlcon.setUseCaches(false);
            //获取连接
            urlcon.connect();
            Date end = new Date();
            is = urlcon.getInputStream();
            buffer = new BufferedReader(new InputStreamReader(is));
            bs = new StringBuffer();
            String l = null;
            while ((l = buffer.readLine()) != null) {
                bs.append(l);
            }
            if (urlcon.getResponseCode() == 200) {
                JSONObject json = JSON.parseObject(bs.toString());
                String ips = String.valueOf(json.get("origin"));
                Object proxy_connection = JSON.parseObject(json.get("headers").toString()).get("Proxy-Connection");
                if (ips.contains(","))
                    type = 2; // 透明
                else if (proxy_connection != null)
                    type = 1; //匿名
                else
                    type = 0; //高匿
                speed = (double) (end.getTime() - start.getTime()) / 1000.00;
            }
            result.put("https", 1);
            result.put("type", type);
            result.put("speed", speed);
            urlcon.disconnect();
            return result;
        } catch (Exception e) {
            result.put("https", 0);
            result.put("type", type);
            result.put("speed", speed);
            return result;
        }finally {
            try {
                if (is != null)
                    is.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
            try {
                if (buffer != null)
                    buffer.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}


text:
using System;
using Microsoft.Extensions.Options;

namespace MGR.CommandLineParser
{
    internal sealed class DefaultParserFactory : IParserFactory
    {
        private readonly IOptions<ParserOptions> _optionsMonitor;
        private readonly IServiceProvider _serviceProvider;

        public DefaultParserFactory(IOptions<ParserOptions> optionsMonitor, IServiceProvider serviceProvider)
        {
            _optionsMonitor = optionsMonitor;
            _serviceProvider = serviceProvider;
        }

        public IParser CreateParser()
        {
            var options = _optionsMonitor.Value;
            var parser = new Parser(options, _serviceProvider);
            return parser;
        }
    }
}


text:
package com.github.dkanellis.skyspark.performance.parsing;

import com.beust.jcommander.IStringConverter;
import com.github.dkanellis.skyspark.performance.result.PointDataFile;

public class PointDataFileConverter implements IStringConverter<PointDataFile> {
    @Override
    public PointDataFile convert(String value) {
        return PointDataFile.fromFilePath(value);
    }
}


text:
class CreateAssetGeometries < ActiveRecord::Migration
  def self.up
    create_table :asset_geometries do |t|
      t.integer :asset_id
      t.string  :style
      t.float   :width
      t.float   :height

      t.timestamps
    end
  end

  def self.down
    drop_table :asset_geometries
  end
end


text:
package com.moac.android.soundmap.injection.module;

import com.facebook.stetho.okhttp.StethoInterceptor;
import com.squareup.okhttp.Interceptor;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import javax.inject.Singleton;

import dagger.Module;
import dagger.Provides;

@Module
public class InstrumentationModule {

    @Provides
    @Singleton
    @ApiModule.NetworkInterceptors
    List<Interceptor> provideNetworkInterceptors() {
        ArrayList<Interceptor> networkInterceptors = new ArrayList<>();
        networkInterceptors.add(new StethoInterceptor());
        return networkInterceptors;
    }

    @Provides
    @Singleton
    @ApiModule.AppInterceptors List<Interceptor> provideAppInterceptors() {
        return Collections.emptyList();
    }
}


text:
import "./unittests/asserts";
import "./unittests/base64";
import "./unittests/builder";
import "./unittests/comments";
import "./unittests/compilerCore";
import "./unittests/convertToBase64";
import "./unittests/customTransforms";
import "./unittests/factory";
import "./unittests/incrementalParser";
import "./unittests/jsDocParsing";
import "./unittests/jsonParserRecovery";
import "./unittests/moduleResolution";
import "./unittests/parsePseudoBigInt";
import "./unittests/paths";
import "./unittests/printer";
import "./unittests/programApi";
import "./unittests/publicApi";
import "./unittests/reuseProgramStructure";
import "./unittests/semver";
import "./unittests/transform";
import "./unittests/typeParameterIsPossiblyReferenced";
import "./unittests/config/commandLineParsing";
import "./unittests/config/configurationExtension";
import "./unittests/config/convertCompilerOptionsFromJson";
import "./unittests/config/convertTypeAcquisitionFromJson";
import "./unittests/config/initializeTSConfig";
import "./unittests/config/matchFiles";
import "./unittests/config/projectReferences";
import "./unittests/config/showConfig";
import "./unittests/config/tsconfigParsing";
import "./unittests/config/tsconfigParsingWatchOptions";
import "./unittests/evaluation/arraySpread";
import "./unittests/evaluation/asyncArrow";
import "./unittests/evaluation/asyncGenerator";
import "./unittests/evaluation/autoAccessors";
import "./unittests/evaluation/awaiter";
import "./unittests/evaluation/destructuring";
import "./unittests/evaluation/externalModules";
import "./unittests/evaluation/forAwaitOf";
import "./unittests/evaluation/forOf";
import "./unittests/evaluation/generator";
import "./unittests/evaluation/optionalCall";
import "./unittests/evaluation/objectRest";
import "./unittests/evaluation/superInStaticInitializer";
import "./unittests/evaluation/templateLiteral";
import "./unittests/evaluation/updateExpressionInModule";
import "./unittests/services/cancellableLanguageServiceOperations";
import "./unittests/services/colorization";
import "./unittests/services/convertToAsyncFunction";
import "./unittests/services/documentRegistry";
import "./unittests/services/extract/constants";
import "./unittests/services/extract/functions";
import "./unittests/services/extract/symbolWalker";
import "./unittests/services/extract/ranges";
import "./unittests/services/hostNewLineSupport";
import "./unittests/services/languageService";
import "./unittests/services/organizeImports";
import "./unittests/services/patternMatcher";
import "./unittests/services/preProcessFile";
import "./unittests/services/textChanges";
import "./unittests/services/transpile";
import "./unittests/tsbuild/amdModulesWithOut";
import "./unittests/tsbuild/clean";
import "./unittests/tsbuild/commandLine";
import "./unittests/tsbuild/configFileErrors";
import "./unittests/tsbuild/configFileExtends";
import "./unittests/tsbuild/containerOnlyReferenced";
import "./unittests/tsbuild/declarationEmit";
import "./unittests/tsbuild/demo";
import "./unittests/tsbuild/emitDeclarationOnly";
import "./unittests/tsbuild/emptyFiles";
import "./unittests/tsbuild/exitCodeOnBogusFile";
import "./unittests/tsbuild/graphOrdering";
import "./unittests/tsbuild/inferredTypeFromTransitiveModule";
import "./unittests/tsbuild/javascriptProjectEmit";
import "./unittests/tsbuild/lateBoundSymbol";
import "./unittests/tsbuild/moduleResolution";
import "./unittests/tsbuild/moduleSpecifiers";
import "./unittests/tsbuild/noEmit";
import "./unittests/tsbuild/noEmitOnError";
import "./unittests/tsbuild/outFile";
import "./unittests/tsbuild/outputPaths";
import "./unittests/tsbuild/publicApi";
import "./unittests/tsbuild/referencesWithRootDirInParent";
import "./unittests/tsbuild/resolveJsonModule";
import "./unittests/tsbuild/sample";
import "./unittests/tsbuild/transitiveReferences";
import "./unittests/tsbuildWatch/configFileErrors";
import "./unittests/tsbuildWatch/demo";
import "./unittests/tsbuildWatch/moduleResolution";
import "./unittests/tsbuildWatch/noEmit";
import "./unittests/tsbuildWatch/noEmitOnError";
import "./unittests/tsbuildWatch/programUpdates";
import "./unittests/tsbuildWatch/projectsBuilding";
import "./unittests/tsbuildWatch/publicApi";
import "./unittests/tsbuildWatch/reexport";
import "./unittests/tsbuildWatch/watchEnvironment";
import "./unittests/tsc/cancellationToken";
import "./unittests/tsc/composite";
import "./unittests/tsc/declarationEmit";
import "./unittests/tsc/forceConsistentCasingInFileNames";
import "./unittests/tsc/incremental";
import "./unittests/tsc/listFilesOnly";
import "./unittests/tsc/projectReferences";
import "./unittests/tsc/redirect";
import "./unittests/tsc/runWithoutArgs";
import "./unittests/tscWatch/consoleClearing";
import "./unittests/tscWatch/emit";
import "./unittests/tscWatch/nodeNextWatch";
import "./unittests/tscWatch/emitAndErrorUpdates";
import "./unittests/tscWatch/forceConsistentCasingInFileNames";
import "./unittests/tscWatch/incremental";
import "./unittests/tscWatch/moduleResolution";
import "./unittests/tscWatch/programUpdates";
import "./unittests/tscWatch/projectsWithReferences";
import "./unittests/tscWatch/resolutionCache";
import "./unittests/tscWatch/sourceOfProjectReferenceRedirect";
import "./unittests/tscWatch/watchApi";
import "./unittests/tscWatch/watchEnvironment";
import "./unittests/tsserver/applyChangesToOpenFiles";
import "./unittests/tsserver/autoImportProvider";
import "./unittests/tsserver/auxiliaryProject";
import "./unittests/tsserver/cachingFileSystemInformation";
import "./unittests/tsserver/cancellationToken";
import "./unittests/tsserver/compileOnSave";
import "./unittests/tsserver/completions";
import "./unittests/tsserver/completionsIncomplete";
import "./unittests/tsserver/configFileSearch";
import "./unittests/tsserver/configuredProjects";
import "./unittests/tsserver/declarationFileMaps";
import "./unittests/tsserver/documentRegistry";
import "./unittests/tsserver/duplicatePackages";
import "./unittests/tsserver/dynamicFiles";
import "./unittests/tsserver/events/largeFileReferenced";
import "./unittests/tsserver/events/projectLanguageServiceState";
import "./unittests/tsserver/events/projectLoading";
import "./unittests/tsserver/events/projectUpdatedInBackground";
import "./unittests/tsserver/exportMapCache";
import "./unittests/tsserver/externalProjects";
import "./unittests/tsserver/forceConsistentCasingInFileNames";
import "./unittests/tsserver/formatSettings";
import "./unittests/tsserver/getApplicableRefactors";
import "./unittests/tsserver/getEditsForFileRename";
import "./unittests/tsserver/getExportReferences";
import "./unittests/tsserver/getFileReferences";
import "./unittests/tsserver/importHelpers";
import "./unittests/tsserver/inlayHints";
import "./unittests/tsserver/inferredProjects";
import "./unittests/tsserver/jsdocTag";
import "./unittests/tsserver/languageService";
import "./unittests/tsserver/maxNodeModuleJsDepth";
import "./unittests/tsserver/metadataInResponse";
import "./unittests/tsserver/moduleResolution";
import "./unittests/tsserver/moduleSpecifierCache";
import "./unittests/tsserver/navTo";
import "./unittests/tsserver/occurences";
import "./unittests/tsserver/openFile";
import "./unittests/tsserver/packageJsonInfo";
import "./unittests/tsserver/partialSemanticServer";
import "./unittests/tsserver/plugins";
import "./unittests/tsserver/projectErrors";
import "./unittests/tsserver/projectReferenceCompileOnSave";
import "./unittests/tsserver/projectReferenceErrors";
import "./unittests/tsserver/projectReferences";
import "./unittests/tsserver/projectReferencesSourcemap";
import "./unittests/tsserver/projects";
import "./unittests/tsserver/projectsWithReferences";
import "./unittests/tsserver/refactors";
import "./unittests/tsserver/reload";
import "./unittests/tsserver/reloadProjects";
import "./unittests/tsserver/rename";
import "./unittests/tsserver/resolutionCache";
import "./unittests/tsserver/session";
import "./unittests/tsserver/skipLibCheck";
import "./unittests/tsserver/smartSelection";
import "./unittests/tsserver/symlinkCache";
import "./unittests/tsserver/symLinks";
import "./unittests/tsserver/syntacticServer";
import "./unittests/tsserver/syntaxOperations";
import "./unittests/tsserver/textStorage";
import "./unittests/tsserver/telemetry";
import "./unittests/tsserver/typeAquisition";
import "./unittests/tsserver/typeOnlyImportChains";
import "./unittests/tsserver/typeReferenceDirectives";
import "./unittests/tsserver/typingsInstaller";
import "./unittests/tsserver/versionCache";
import "./unittests/tsserver/watchEnvironment";
import "./unittests/tsserver/webServer";
import "./unittests/debugDeprecation";


text:
.class Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;
.super Lcom/android/internal/util/State;
.source "WifiWatchdogStateMachine.java"

# annotations
.annotation system Ldalvik/annotation/EnclosingClass;
    value = Lcom/android/server/wifi/WifiWatchdogStateMachine;
.end annotation

.annotation system Ldalvik/annotation/InnerClass;
    accessFlags = 0x0
    name = "LinkMonitoringState"
.end annotation

# instance fields
.field private mLastRssi:I

.field private mLastTxBad:I

.field private mLastTxGood:I

.field private mSampleCount:I

.field final synthetic this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

# direct methods
.method constructor <init>(Lcom/android/server/wifi/WifiWatchdogStateMachine;)V
    .locals 0
    .param p1, "this$0"    # Lcom/android/server/wifi/WifiWatchdogStateMachine;

    .prologue
    .line 745
    iput-object p1, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    invoke-direct {p0}, Lcom/android/internal/util/State;-><init>()V

    return-void
.end method

# virtual methods
.method public enter()V
    .locals 7

    .prologue
    const/4 v6, 0x0

    .line 756
    iput v6, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mSampleCount:I

    .line 757
    iget-object v0, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    new-instance v1, Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;

    iget-object v2, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    const-wide/high16 v4, 0x3fe0000000000000L    # 0.5

    invoke-direct {v1, v2, v4, v5}, Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;-><init>(Lcom/android/server/wifi/WifiWatchdogStateMachine;D)V

    invoke-static {v0, v1}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-set0(Lcom/android/server/wifi/WifiWatchdogStateMachine;Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;)Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;

    .line 758
    iget-object v0, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    iget-object v1, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    iget-object v2, p0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    invoke-static {v2}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get11(Lcom/android/server/wifi/WifiWatchdogStateMachine;)I

    move-result v3

    add-int/lit8 v3, v3, 0x1

    invoke-static {v2, v3}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-set4(Lcom/android/server/wifi/WifiWatchdogStateMachine;I)I

    move-result v2

    const v3, 0x2100b

    invoke-virtual {v1, v3, v2, v6}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->obtainMessage(III)Landroid/os/Message;

    move-result-object v1

    invoke-virtual {v0, v1}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->sendMessage(Landroid/os/Message;)V

    .line 754
    return-void
.end method

.method public processMessage(Landroid/os/Message;)Z
    .locals 21
    .param p1, "msg"    # Landroid/os/Message;

    .prologue
    .line 763
    move-object/from16 v0, p1

    iget v0, v0, Landroid/os/Message;->what:I

    move/from16 v16, v0

    sparse-switch v16, :sswitch_data_0

    .line 850
    const/16 v16, 0x0

    return v16

    .line 765
    :sswitch_0
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v17, v0

    move-object/from16 v0, p1

    iget v0, v0, Landroid/os/Message;->arg1:I

    move/from16 v18, v0

    invoke-static/range {v17 .. v18}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-wrap2(Lcom/android/server/wifi/WifiWatchdogStateMachine;I)I

    move-result v17

    invoke-static/range {v16 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-set1(Lcom/android/server/wifi/WifiWatchdogStateMachine;I)I

    .line 766
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get4(Lcom/android/server/wifi/WifiWatchdogStateMachine;)I

    move-result v16

    const/16 v17, 0x4

    move/from16 v0, v16

    move/from16 v1, v17

    if-gt v0, v1, :cond_1

    .line 852
    :cond_0
    :goto_0
    :sswitch_1
    const/16 v16, 0x1

    return v16

    .line 770
    :cond_1
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v17, v0

    invoke-static/range {v17 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get9(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$OnlineWatchState;

    move-result-object v17

    invoke-static/range {v16 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-wrap5(Lcom/android/server/wifi/WifiWatchdogStateMachine;Lcom/android/internal/util/IState;)V

    goto :goto_0

    .line 775
    :sswitch_2
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v17, v0

    invoke-static/range {v17 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get6(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;

    move-result-object v17

    invoke-static/range {v16 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-wrap5(Lcom/android/server/wifi/WifiWatchdogStateMachine;Lcom/android/internal/util/IState;)V

    goto :goto_0

    .line 779
    :sswitch_3
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get5(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Z

    move-result v16

    if-nez v16, :cond_2

    .line 780
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v17, v0

    invoke-static/range {v17 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get8(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$OnlineState;

    move-result-object v17

    invoke-static/range {v16 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-wrap5(Lcom/android/server/wifi/WifiWatchdogStateMachine;Lcom/android/internal/util/IState;)V

    goto :goto_0

    .line 781
    :cond_2
    move-object/from16 v0, p1

    iget v0, v0, Landroid/os/Message;->arg1:I

    move/from16 v16, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v17, v0

    invoke-static/range {v17 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get11(Lcom/android/server/wifi/WifiWatchdogStateMachine;)I

    move-result v17

    move/from16 v0, v16

    move/from16 v1, v17

    if-ne v0, v1, :cond_0

    .line 782
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get16(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/internal/util/AsyncChannel;

    move-result-object v16

    const v17, 0x25014

    invoke-virtual/range {v16 .. v17}, Lcom/android/internal/util/AsyncChannel;->sendMessage(I)V

    .line 783
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v17, v0

    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v18, v0

    invoke-static/range {v18 .. v18}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get11(Lcom/android/server/wifi/WifiWatchdogStateMachine;)I

    move-result v19

    add-int/lit8 v19, v19, 0x1

    invoke-static/range {v18 .. v19}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-set4(Lcom/android/server/wifi/WifiWatchdogStateMachine;I)I

    move-result v18

    const v19, 0x2100b

    const/16 v20, 0x0

    move-object/from16 v0, v17

    move/from16 v1, v19

    move/from16 v2, v18

    move/from16 v3, v20

    invoke-virtual {v0, v1, v2, v3}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->obtainMessage(III)Landroid/os/Message;

    move-result-object v17

    .line 784
    const-wide/16 v18, 0x3e8

    .line 783
    invoke-virtual/range {v16 .. v19}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->sendMessageDelayed(Landroid/os/Message;J)V

    goto/16 :goto_0

    .line 789
    :sswitch_4
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get2(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;

    move-result-object v16

    if-eqz v16, :cond_0

    .line 792
    move-object/from16 v0, p1

    iget-object v7, v0, Landroid/os/Message;->obj:Ljava/lang/Object;

    check-cast v7, Landroid/net/wifi/RssiPacketCountInfo;

    .line 793
    .local v7, "info":Landroid/net/wifi/RssiPacketCountInfo;
    iget v11, v7, Landroid/net/wifi/RssiPacketCountInfo;->rssi:I

    .line 794
    .local v11, "rssi":I
    move-object/from16 v0, p0

    iget v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mLastRssi:I

    move/from16 v16, v0

    add-int v16, v16, v11

    div-int/lit8 v10, v16, 0x2

    .line 795
    .local v10, "mrssi":I
    iget v14, v7, Landroid/net/wifi/RssiPacketCountInfo;->txbad:I

    .line 796
    .local v14, "txbad":I
    iget v15, v7, Landroid/net/wifi/RssiPacketCountInfo;->txgood:I

    .line 801
    .local v15, "txgood":I
    invoke-static {}, Landroid/os/SystemClock;->elapsedRealtime()J

    move-result-wide v12

    .line 802
    .local v12, "now":J
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get2(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;

    move-result-object v16

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;->-get4(Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;)J

    move-result-wide v16

    sub-long v16, v12, v16

    const-wide/16 v18, 0x7d0

    cmp-long v16, v16, v18

    if-gez v16, :cond_3

    .line 805
    move-object/from16 v0, p0

    iget v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mLastTxBad:I

    move/from16 v16, v0

    sub-int v4, v14, v16

    .line 806
    .local v4, "dbad":I
    move-object/from16 v0, p0

    iget v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mLastTxGood:I

    move/from16 v16, v0

    sub-int v5, v15, v16

    .line 807
    .local v5, "dgood":I
    add-int v6, v4, v5

    .line 809
    .local v6, "dtotal":I
    if-lez v6, :cond_3

    .line 811
    int-to-double v0, v4

    move-wide/from16 v16, v0

    int-to-double v0, v6

    move-wide/from16 v18, v0

    div-double v8, v16, v18

    .line 813
    .local v8, "loss":D
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get3(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;

    move-result-object v16

    move-object/from16 v0, v16

    invoke-virtual {v0, v8, v9, v6}, Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;->update(DI)V

    .line 822
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get2(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;

    move-result-object v16

    move-object/from16 v0, v16

    invoke-virtual {v0, v10, v8, v9, v6}, Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;->updateLoss(IDI)V

    .line 825
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get3(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;

    move-result-object v16

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;->-get0(Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;)D

    move-result-wide v16

    const-wide/high16 v18, 0x3fe0000000000000L    # 0.5

    cmpl-double v16, v16, v18

    if-lez v16, :cond_4

    .line 826
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get3(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;

    move-result-object v16

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;->-get1(Lcom/android/server/wifi/WifiWatchdogStateMachine$VolumeWeightedEMA;)D

    move-result-wide v16

    const-wide/high16 v18, 0x4000000000000000L    # 2.0

    cmpl-double v16, v16, v18

    if-lez v16, :cond_4

    .line 827
    move-object/from16 v0, p0

    iget v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mSampleCount:I

    move/from16 v16, v0

    add-int/lit8 v16, v16, 0x1

    move/from16 v0, v16

    move-object/from16 v1, p0

    iput v0, v1, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mSampleCount:I

    const/16 v17, 0x3

    move/from16 v0, v16

    move/from16 v1, v17

    if-lt v0, v1, :cond_3

    .line 828
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get2(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;

    move-result-object v16

    move-object/from16 v0, v16

    invoke-virtual {v0, v11}, Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;->poorLinkDetected(I)Z

    move-result v16

    if-eqz v16, :cond_3

    .line 829
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    const/16 v17, 0x0

    invoke-static/range {v16 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-wrap4(Lcom/android/server/wifi/WifiWatchdogStateMachine;Z)V

    .line 830
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get11(Lcom/android/server/wifi/WifiWatchdogStateMachine;)I

    move-result v17

    add-int/lit8 v17, v17, 0x1

    invoke-static/range {v16 .. v17}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-set4(Lcom/android/server/wifi/WifiWatchdogStateMachine;I)I

    .line 838
    .end local v4    # "dbad":I
    .end local v5    # "dgood":I
    .end local v6    # "dtotal":I
    .end local v8    # "loss":D
    :cond_3
    :goto_1
    move-object/from16 v0, p0

    iget-object v0, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->this$0:Lcom/android/server/wifi/WifiWatchdogStateMachine;

    move-object/from16 v16, v0

    invoke-static/range {v16 .. v16}, Lcom/android/server/wifi/WifiWatchdogStateMachine;->-get2(Lcom/android/server/wifi/WifiWatchdogStateMachine;)Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;

    move-result-object v16

    move-object/from16 v0, v16

    invoke-static {v0, v12, v13}, Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;->-set3(Lcom/android/server/wifi/WifiWatchdogStateMachine$BssidStatistics;J)J

    .line 839
    move-object/from16 v0, p0

    iput v14, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mLastTxBad:I

    .line 840
    move-object/from16 v0, p0

    iput v15, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mLastTxGood:I

    .line 841
    move-object/from16 v0, p0

    iput v11, v0, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mLastRssi:I

    goto/16 :goto_0

    .line 833
    .restart local v4    # "dbad":I
    .restart local v5    # "dgood":I
    .restart local v6    # "dtotal":I
    .restart local v8    # "loss":D
    :cond_4
    const/16 v16, 0x0

    move/from16 v0, v16

    move-object/from16 v1, p0

    iput v0, v1, Lcom/android/server/wifi/WifiWatchdogStateMachine$LinkMonitoringState;->mSampleCount:I

    goto :goto_1

    .line 763
    :sswitch_data_0
    .sparse-switch
        0x21003 -> :sswitch_0
        0x21007 -> :sswitch_2
        0x2100b -> :sswitch_3
        0x25015 -> :sswitch_4
        0x25016 -> :sswitch_1
    .end sparse-switch
.end method


text:
package org.apache.drill.exec.server.rest.auth;

import org.apache.drill.exec.rpc.security.plain.PlainFactory;
import org.apache.drill.shaded.guava.com.google.common.collect.ImmutableSet;
import org.apache.drill.common.exceptions.DrillException;
import org.apache.drill.exec.server.DrillbitContext;
import org.eclipse.jetty.security.ConstraintMapping;
import org.eclipse.jetty.security.ConstraintSecurityHandler;
import org.eclipse.jetty.security.LoginService;
import org.eclipse.jetty.security.authentication.LoginAuthenticator;

import java.util.Collections;
import java.util.Set;

import static org.apache.drill.exec.server.rest.auth.DrillUserPrincipal.ADMIN_ROLE;
import static org.apache.drill.exec.server.rest.auth.DrillUserPrincipal.AUTHENTICATED_ROLE;

/**
 * Accessor class that extends the {@link ConstraintSecurityHandler} to expose
 * protected method's for start and stop of Handler. This is needed since now
 * {@code DrillHttpSecurityHandlerProvider} composes of 2 security handlers -
 * For FORM and SPNEGO and has responsibility to start/stop of those handlers.
 **/
public abstract class DrillHttpConstraintSecurityHandler extends ConstraintSecurityHandler {

  @Override
  public void doStart() throws Exception {
    super.doStart();
  }

  @Override
  public void doStop() throws Exception {
    super.doStop();
  }

  public abstract void doSetup(DrillbitContext dbContext) throws DrillException;

  public void setup(LoginAuthenticator authenticator, LoginService loginService) {
    final Set<String> knownRoles = ImmutableSet.of(AUTHENTICATED_ROLE, ADMIN_ROLE);
    setConstraintMappings(Collections.<ConstraintMapping>emptyList(), knownRoles);
    setAuthenticator(authenticator);
    setLoginService(loginService);
  }

  protected void requireAuthProvider(DrillbitContext dbContext, String name) throws DrillException {
    // Check if PAMAuthenticator is available or not which is required for FORM authentication
    if (!dbContext.getAuthProvider().containsFactory(PlainFactory.SIMPLE_NAME)) {
      throw new DrillException(String.format("%1$s auth mechanism was configured but %2$s mechanism is not enabled to provide an " +
        "authenticator. Please configure user authentication with %2$s mechanism and authenticator to use " +
        "%1$s authentication", getImplName(), name));
    }
  }

  public abstract String getImplName();
}


text:
module ExtendedRuby
  VERSION = "0.0.22"
end


text:
require 'minitest/autorun'

def windows?
  RbConfig::CONFIG['target_os'] =~ /mingw32|mswin/
end

def darwin?
  RbConfig::CONFIG['target_os'] =~ /darwin/
end

def nix?
  ! (darwin? || windows?)
end

if darwin?
  require_relative '../lib/fast_slice.bundle'
elsif nix?
  require_relative '../lib/fast_slice.so'
else
  raise "Sorry, that platform isn't supported"
end


text:
Rob's ESP extended port
=======================
Changes over upstream
--------------------
* wifi events manager `(esp.wifi_events.init)`
* esp smart config (esp.smartconfig)
* Queuing between interrupt io and python user space.
* Attachment of GPIO interrupts to buttons and user task scheduling
  You can have a python function called when an interrupt driven button is pressed.
* Software debouncing of switches for interrupt queued tasks
* Interrupt drivern GPIO
* Full interrupt driven DHT22 temperature and humidity sensor.
* ESP SDK os task scheduling.
* Dallas 1 Wire protocol. (Soon to have interrupt driven notiifcation, such as conversion but not support by my DS hardware).
* I2C on any lines.
* Frozen code is all in the word addressable SPI rom. Byte level unpacking is supported.
* Mutexes using assembly language and a python wrapper.
* ESP OS timers.
* Updates tcp/ip (now stress tested over 100s of hours and 100% stable so far).

Notes
-----
    Now building wih the 1.5 version of the ESP SDK.

The MicroPython project
=======================

This is the MicroPython project, which aims to put an implementation
of Python 3.x on microcontrollers and small embedded systems.

WARNING: this project is in beta stage and is subject to changes of the
code-base, including project-wide name changes and API changes.

MicroPython implements the entire Python 3.4 syntax (including exceptions,
"with", "yield from", etc.).  The following core datatypes are provided:
str (including basic Unicode support), bytes, bytearray, tuple, list, dict,
set, frozenset, array.array, collections.namedtuple, classes and instances.
Builtin modules include sys, time, and struct.  Note that only subset of
Python 3.4 functionality implemented for the data types and modules.

See the repository www.github.com/micropython/pyboard for the Micro
Python board, the officially supported reference electronic circuit board.

Major components in this repository:
- py/ -- the core Python implementation, including compiler, runtime, and
  core library.
- unix/ -- a version of MicroPython that runs on Unix.
- stmhal/ -- a version of MicroPython that runs on the MicroPython board
  with an STM32F405RG (using ST's Cube HAL drivers).
- minimal/ -- a minimal MicroPython port. Start with this if you want
  to port MicroPython to another microcontroller.

Additional components:
- bare-arm/ -- a bare minimum version of MicroPython for ARM MCUs. Used
  mostly to control code size.
- teensy/ -- a version of MicroPython that runs on the Teensy 3.1
  (preliminary but functional).
- pic16bit/ -- a version of MicroPython for 16-bit PIC microcontrollers.
- cc3200/ -- a version of MicroPython that runs on the CC3200 from TI.
- esp8266/ -- an experimental port for ESP8266 WiFi modules.
- tests/ -- test framework and test scripts.
- tools/ -- various tools, including the pyboard.py module.
- examples/ -- a few example Python scripts.
- docs/ -- official documentation in RST format.

"make" is used to build the components, or "gmake" on BSD-based systems.
You will also need bash and Python (at least 2.7 or 3.3).

The Unix version
----------------

The "unix" port requires a standard Unix environment with gcc and GNU make.
x86 and x64 architectures are supported (i.e. x86 32- and 64-bit), as well
as ARM and MIPS. Making full-featured port to another architecture requires
writing some assembly code for the exception handling and garbage collection.
Alternatively, fallback implementation based on setjmp/longjmp can be used.

To build (*):

    $ cd unix
    $ make

Then to give it a try:

    $ ./micropython
    >>> list(5 * x + y for x in range(10) for y in [4, 2, 1])

Use `CTRL-D` (i.e. EOF) to exit the shell.
Learn about command-line options (in particular, how to increase heap size
which may be needed for larger applications):

    $ ./micropython --help

Run complete testsuite:

    $ make test

Unix version comes with a builtin package manager called upip, e.g.:

    $ ./micropython -m upip install micropython-pystone
    $ ./micropython -m pystone

Browse available modules on
[PyPI](https://pypi.python.org/pypi?%3Aaction=search&term=micropython).
Standard library modules come from
[micropython-lib](https://github.com/micropython/micropython-lib) project.

External dependencies
---------------------

Building Unix version requires some dependencies installed. For
Debian/Ubuntu/Mint derivative Linux distros, install `build-essential`
(includes toolchain and make), `libffi-dev`, and `pkg-config` packages.

Other dependencies can be built together with MicroPython. Oftentimes,
you need to do this to enable extra features or capabilities. To build
these additional dependencies, first fetch git submodules for them:

    $ git submodule update --init

Use this same command to get the latest versions of dependencies, as
they are updated from time to time. After that, in `unix/` dir, execute:

    $ make deplibs

This will build all available dependencies (regardless whether they
are used or not). If you intend to build MicroPython with additional
options (like cross-compiling), the same set of options should be passed
to `make deplibs`. To actually enabled use of dependencies, edit
`unix/mpconfigport.mk` file, which has inline descriptions of the options.
For example, to build SSL module (required for `upip` tool described above),
set `MICROPY_PY_USSL` to 1.

In `unix/mpconfigport.mk`, you can also disable some dependencies enabled
by default, like FFI support, which requires libffi development files to
be installed.

The STM version
---------------

The "stmhal" port requires an ARM compiler, arm-none-eabi-gcc, and associated
bin-utils.  For those using Arch Linux, you need arm-none-eabi-binutils and
arm-none-eabi-gcc packages from the AUR.  Otherwise, try here:
https://launchpad.net/gcc-arm-embedded

To build:

    $ cd stmhal
    $ make

You then need to get your board into DFU mode.  On the pyboard, connect the
3V3 pin to the P1/DFU pin with a wire (on PYBv1.0 they are next to each other
on the bottom left of the board, second row from the bottom).

Then to flash the code via USB DFU to your device:

    $ make deploy

You will need the dfu-util program, on Arch Linux it's dfu-util-git in the
AUR.  If the above does not work it may be because you don't have the
correct permissions.  Try then:

    $ sudo dfu-util -a 0 -d 0483:df11 -D build-PYBV10/firmware.dfu