1207340Sjkim/****************************************************************************** 2207340Sjkim * 3207340Sjkim * Module Name: aslrestype1i - Small I/O-related resource descriptors 4207340Sjkim * 5207340Sjkim *****************************************************************************/ 6207340Sjkim 7217365Sjkim/* 8245582Sjkim * Copyright (C) 2000 - 2013, Intel Corp. 9207340Sjkim * All rights reserved. 10207340Sjkim * 11217365Sjkim * Redistribution and use in source and binary forms, with or without 12217365Sjkim * modification, are permitted provided that the following conditions 13217365Sjkim * are met: 14217365Sjkim * 1. Redistributions of source code must retain the above copyright 15217365Sjkim * notice, this list of conditions, and the following disclaimer, 16217365Sjkim * without modification. 17217365Sjkim * 2. Redistributions in binary form must reproduce at minimum a disclaimer 18217365Sjkim * substantially similar to the "NO WARRANTY" disclaimer below 19217365Sjkim * ("Disclaimer") and any redistribution must be conditioned upon 20217365Sjkim * including a substantially similar Disclaimer requirement for further 21217365Sjkim * binary redistribution. 22217365Sjkim * 3. Neither the names of the above-listed copyright holders nor the names 23217365Sjkim * of any contributors may be used to endorse or promote products derived 24217365Sjkim * from this software without specific prior written permission. 25207340Sjkim * 26217365Sjkim * Alternatively, this software may be distributed under the terms of the 27217365Sjkim * GNU General Public License ("GPL") version 2 as published by the Free 28217365Sjkim * Software Foundation. 29207340Sjkim * 30217365Sjkim * NO WARRANTY 31217365Sjkim * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 32217365Sjkim * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 33217365Sjkim * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR 34217365Sjkim * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 35217365Sjkim * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 36217365Sjkim * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 37217365Sjkim * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 38217365Sjkim * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 39217365Sjkim * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING 40217365Sjkim * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 41217365Sjkim * POSSIBILITY OF SUCH DAMAGES. 42217365Sjkim */ 43207340Sjkim 44207340Sjkim 45207344Sjkim#include <contrib/dev/acpica/compiler/aslcompiler.h> 46207340Sjkim#include "aslcompiler.y.h" 47207340Sjkim 48207340Sjkim#define _COMPONENT ACPI_COMPILER 49207340Sjkim ACPI_MODULE_NAME ("aslrestype1i") 50207340Sjkim 51207340Sjkim/* 52207340Sjkim * This module contains the I/O-related small resource descriptors: 53207340Sjkim * 54207340Sjkim * DMA 55228110Sjkim * FixedDMA 56207340Sjkim * FixedIO 57207340Sjkim * IO 58207340Sjkim * IRQ 59207340Sjkim * IRQNoFlags 60207340Sjkim */ 61207340Sjkim 62207340Sjkim/******************************************************************************* 63207340Sjkim * 64207340Sjkim * FUNCTION: RsDoDmaDescriptor 65207340Sjkim * 66207340Sjkim * PARAMETERS: Op - Parent resource descriptor parse node 67207340Sjkim * CurrentByteOffset - Offset into the resource template AML 68207340Sjkim * buffer (to track references to the desc) 69207340Sjkim * 70207340Sjkim * RETURN: Completed resource node 71207340Sjkim * 72207340Sjkim * DESCRIPTION: Construct a short "DMA" descriptor 73207340Sjkim * 74207340Sjkim ******************************************************************************/ 75207340Sjkim 76207340SjkimASL_RESOURCE_NODE * 77207340SjkimRsDoDmaDescriptor ( 78207340Sjkim ACPI_PARSE_OBJECT *Op, 79207340Sjkim UINT32 CurrentByteOffset) 80207340Sjkim{ 81207340Sjkim AML_RESOURCE *Descriptor; 82207340Sjkim ACPI_PARSE_OBJECT *InitializerOp; 83207340Sjkim ASL_RESOURCE_NODE *Rnode; 84207340Sjkim UINT32 i; 85207340Sjkim UINT8 DmaChannelMask = 0; 86207340Sjkim UINT8 DmaChannels = 0; 87207340Sjkim 88207340Sjkim 89207340Sjkim InitializerOp = Op->Asl.Child; 90207340Sjkim Rnode = RsAllocateResourceNode (sizeof (AML_RESOURCE_DMA)); 91207340Sjkim 92207340Sjkim Descriptor = Rnode->Buffer; 93207340Sjkim Descriptor->Dma.DescriptorType = ACPI_RESOURCE_NAME_DMA | 94207340Sjkim ASL_RDESC_DMA_SIZE; 95207340Sjkim 96207340Sjkim /* Process all child initialization nodes */ 97207340Sjkim 98207340Sjkim for (i = 0; InitializerOp; i++) 99207340Sjkim { 100207340Sjkim switch (i) 101207340Sjkim { 102207340Sjkim case 0: /* DMA type */ 103207340Sjkim 104207340Sjkim RsSetFlagBits (&Descriptor->Dma.Flags, InitializerOp, 5, 0); 105228110Sjkim RsCreateMultiBitField (InitializerOp, ACPI_RESTAG_DMATYPE, 106228110Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Dma.Flags), 5, 2); 107207340Sjkim break; 108207340Sjkim 109207340Sjkim case 1: /* Bus Master */ 110207340Sjkim 111207340Sjkim RsSetFlagBits (&Descriptor->Dma.Flags, InitializerOp, 2, 0); 112207340Sjkim RsCreateBitField (InitializerOp, ACPI_RESTAG_BUSMASTER, 113207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Dma.Flags), 2); 114207340Sjkim break; 115207340Sjkim 116207340Sjkim case 2: /* Xfer Type (transfer width) */ 117207340Sjkim 118207340Sjkim RsSetFlagBits (&Descriptor->Dma.Flags, InitializerOp, 0, 0); 119228110Sjkim RsCreateMultiBitField (InitializerOp, ACPI_RESTAG_XFERTYPE, 120228110Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Dma.Flags), 0, 2); 121207340Sjkim break; 122207340Sjkim 123207340Sjkim case 3: /* Name */ 124207340Sjkim 125207340Sjkim UtAttachNamepathToOwner (Op, InitializerOp); 126207340Sjkim break; 127207340Sjkim 128207340Sjkim default: 129207340Sjkim 130207340Sjkim /* All DMA channel bytes are handled here, after flags and name */ 131207340Sjkim 132207340Sjkim if (InitializerOp->Asl.ParseOpcode != PARSEOP_DEFAULT_ARG) 133207340Sjkim { 134207340Sjkim /* Up to 8 channels can be specified in the list */ 135207340Sjkim 136207340Sjkim DmaChannels++; 137207340Sjkim if (DmaChannels > 8) 138207340Sjkim { 139207340Sjkim AslError (ASL_ERROR, ASL_MSG_DMA_LIST, 140207340Sjkim InitializerOp, NULL); 141207340Sjkim return (Rnode); 142207340Sjkim } 143207340Sjkim 144207340Sjkim /* Only DMA channels 0-7 are allowed (mask is 8 bits) */ 145207340Sjkim 146207340Sjkim if (InitializerOp->Asl.Value.Integer > 7) 147207340Sjkim { 148207340Sjkim AslError (ASL_ERROR, ASL_MSG_DMA_CHANNEL, 149207340Sjkim InitializerOp, NULL); 150207340Sjkim } 151207340Sjkim 152207340Sjkim /* Build the mask */ 153207340Sjkim 154207340Sjkim DmaChannelMask |= 155207340Sjkim (1 << ((UINT8) InitializerOp->Asl.Value.Integer)); 156207340Sjkim } 157207340Sjkim 158207340Sjkim if (i == 4) /* case 4: First DMA byte */ 159207340Sjkim { 160207340Sjkim /* Check now for duplicates in list */ 161207340Sjkim 162207340Sjkim RsCheckListForDuplicates (InitializerOp); 163207340Sjkim 164207340Sjkim /* Create a named field at the start of the list */ 165207340Sjkim 166207340Sjkim RsCreateByteField (InitializerOp, ACPI_RESTAG_DMA, 167207340Sjkim CurrentByteOffset + 168207340Sjkim ASL_RESDESC_OFFSET (Dma.DmaChannelMask)); 169207340Sjkim } 170207340Sjkim break; 171207340Sjkim } 172207340Sjkim 173207340Sjkim InitializerOp = RsCompleteNodeAndGetNext (InitializerOp); 174207340Sjkim } 175207340Sjkim 176207340Sjkim /* Now we can set the channel mask */ 177207340Sjkim 178207340Sjkim Descriptor->Dma.DmaChannelMask = DmaChannelMask; 179207340Sjkim return (Rnode); 180207340Sjkim} 181207340Sjkim 182207340Sjkim 183207340Sjkim/******************************************************************************* 184207340Sjkim * 185228110Sjkim * FUNCTION: RsDoFixedDmaDescriptor 186228110Sjkim * 187228110Sjkim * PARAMETERS: Op - Parent resource descriptor parse node 188228110Sjkim * CurrentByteOffset - Offset into the resource template AML 189228110Sjkim * buffer (to track references to the desc) 190228110Sjkim * 191228110Sjkim * RETURN: Completed resource node 192228110Sjkim * 193228110Sjkim * DESCRIPTION: Construct a short "FixedDMA" descriptor 194228110Sjkim * 195228110Sjkim ******************************************************************************/ 196228110Sjkim 197228110SjkimASL_RESOURCE_NODE * 198228110SjkimRsDoFixedDmaDescriptor ( 199228110Sjkim ACPI_PARSE_OBJECT *Op, 200228110Sjkim UINT32 CurrentByteOffset) 201228110Sjkim{ 202228110Sjkim AML_RESOURCE *Descriptor; 203228110Sjkim ACPI_PARSE_OBJECT *InitializerOp; 204228110Sjkim ASL_RESOURCE_NODE *Rnode; 205228110Sjkim UINT32 i; 206228110Sjkim 207228110Sjkim 208228110Sjkim InitializerOp = Op->Asl.Child; 209228110Sjkim Rnode = RsAllocateResourceNode (sizeof (AML_RESOURCE_FIXED_DMA)); 210228110Sjkim 211228110Sjkim Descriptor = Rnode->Buffer; 212228110Sjkim Descriptor->FixedDma.DescriptorType = 213228110Sjkim ACPI_RESOURCE_NAME_FIXED_DMA | ASL_RDESC_FIXED_DMA_SIZE; 214228110Sjkim 215228110Sjkim /* Process all child initialization nodes */ 216228110Sjkim 217228110Sjkim for (i = 0; InitializerOp; i++) 218228110Sjkim { 219228110Sjkim switch (i) 220228110Sjkim { 221228110Sjkim case 0: /* DMA Request Lines [WORD] (_DMA) */ 222228110Sjkim 223228110Sjkim Descriptor->FixedDma.RequestLines = (UINT16) InitializerOp->Asl.Value.Integer; 224228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_DMA, 225228110Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (FixedDma.RequestLines)); 226228110Sjkim break; 227228110Sjkim 228228110Sjkim case 1: /* DMA Channel [WORD] (_TYP) */ 229228110Sjkim 230228110Sjkim Descriptor->FixedDma.Channels = (UINT16) InitializerOp->Asl.Value.Integer; 231228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_DMATYPE, 232228110Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (FixedDma.Channels)); 233228110Sjkim break; 234228110Sjkim 235228110Sjkim case 2: /* Transfer Width [BYTE] (_SIZ) */ 236228110Sjkim 237228110Sjkim Descriptor->FixedDma.Width = (UINT8) InitializerOp->Asl.Value.Integer; 238228110Sjkim RsCreateByteField (InitializerOp, ACPI_RESTAG_XFERTYPE, 239228110Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (FixedDma.Width)); 240228110Sjkim break; 241228110Sjkim 242228110Sjkim case 3: /* Descriptor Name (optional) */ 243228110Sjkim 244228110Sjkim UtAttachNamepathToOwner (Op, InitializerOp); 245228110Sjkim break; 246228110Sjkim 247228110Sjkim default: /* Ignore any extra nodes */ 248250838Sjkim 249228110Sjkim break; 250228110Sjkim } 251228110Sjkim 252228110Sjkim InitializerOp = RsCompleteNodeAndGetNext (InitializerOp); 253228110Sjkim } 254228110Sjkim 255228110Sjkim return (Rnode); 256228110Sjkim} 257228110Sjkim 258228110Sjkim 259228110Sjkim/******************************************************************************* 260228110Sjkim * 261207340Sjkim * FUNCTION: RsDoFixedIoDescriptor 262207340Sjkim * 263207340Sjkim * PARAMETERS: Op - Parent resource descriptor parse node 264207340Sjkim * CurrentByteOffset - Offset into the resource template AML 265207340Sjkim * buffer (to track references to the desc) 266207340Sjkim * 267207340Sjkim * RETURN: Completed resource node 268207340Sjkim * 269207340Sjkim * DESCRIPTION: Construct a short "FixedIO" descriptor 270207340Sjkim * 271207340Sjkim ******************************************************************************/ 272207340Sjkim 273207340SjkimASL_RESOURCE_NODE * 274207340SjkimRsDoFixedIoDescriptor ( 275207340Sjkim ACPI_PARSE_OBJECT *Op, 276207340Sjkim UINT32 CurrentByteOffset) 277207340Sjkim{ 278207340Sjkim AML_RESOURCE *Descriptor; 279207340Sjkim ACPI_PARSE_OBJECT *InitializerOp; 280207340Sjkim ACPI_PARSE_OBJECT *AddressOp = NULL; 281207340Sjkim ASL_RESOURCE_NODE *Rnode; 282207340Sjkim UINT32 i; 283207340Sjkim 284207340Sjkim 285207340Sjkim InitializerOp = Op->Asl.Child; 286207340Sjkim Rnode = RsAllocateResourceNode (sizeof (AML_RESOURCE_FIXED_IO)); 287207340Sjkim 288207340Sjkim Descriptor = Rnode->Buffer; 289207340Sjkim Descriptor->Io.DescriptorType = ACPI_RESOURCE_NAME_FIXED_IO | 290207340Sjkim ASL_RDESC_FIXED_IO_SIZE; 291207340Sjkim 292207340Sjkim /* Process all child initialization nodes */ 293207340Sjkim 294207340Sjkim for (i = 0; InitializerOp; i++) 295207340Sjkim { 296207340Sjkim switch (i) 297207340Sjkim { 298207340Sjkim case 0: /* Base Address */ 299207340Sjkim 300207340Sjkim Descriptor->FixedIo.Address = 301207340Sjkim (UINT16) InitializerOp->Asl.Value.Integer; 302228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_BASEADDRESS, 303207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (FixedIo.Address)); 304207340Sjkim AddressOp = InitializerOp; 305207340Sjkim break; 306207340Sjkim 307207340Sjkim case 1: /* Length */ 308207340Sjkim 309207340Sjkim Descriptor->FixedIo.AddressLength = 310207340Sjkim (UINT8) InitializerOp->Asl.Value.Integer; 311207340Sjkim RsCreateByteField (InitializerOp, ACPI_RESTAG_LENGTH, 312207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (FixedIo.AddressLength)); 313207340Sjkim break; 314207340Sjkim 315207340Sjkim case 2: /* Name */ 316207340Sjkim 317207340Sjkim UtAttachNamepathToOwner (Op, InitializerOp); 318207340Sjkim break; 319207340Sjkim 320207340Sjkim default: 321207340Sjkim 322207340Sjkim AslError (ASL_ERROR, ASL_MSG_RESOURCE_LIST, InitializerOp, NULL); 323207340Sjkim break; 324207340Sjkim } 325207340Sjkim 326207340Sjkim InitializerOp = RsCompleteNodeAndGetNext (InitializerOp); 327207340Sjkim } 328207340Sjkim 329207340Sjkim /* Error checks */ 330207340Sjkim 331207340Sjkim if (Descriptor->FixedIo.Address > 0x03FF) 332207340Sjkim { 333207340Sjkim AslError (ASL_WARNING, ASL_MSG_ISA_ADDRESS, AddressOp, NULL); 334207340Sjkim } 335207340Sjkim 336207340Sjkim return (Rnode); 337207340Sjkim} 338207340Sjkim 339207340Sjkim 340207340Sjkim/******************************************************************************* 341207340Sjkim * 342207340Sjkim * FUNCTION: RsDoIoDescriptor 343207340Sjkim * 344207340Sjkim * PARAMETERS: Op - Parent resource descriptor parse node 345207340Sjkim * CurrentByteOffset - Offset into the resource template AML 346207340Sjkim * buffer (to track references to the desc) 347207340Sjkim * 348207340Sjkim * RETURN: Completed resource node 349207340Sjkim * 350207340Sjkim * DESCRIPTION: Construct a short "IO" descriptor 351207340Sjkim * 352207340Sjkim ******************************************************************************/ 353207340Sjkim 354207340SjkimASL_RESOURCE_NODE * 355207340SjkimRsDoIoDescriptor ( 356207340Sjkim ACPI_PARSE_OBJECT *Op, 357207340Sjkim UINT32 CurrentByteOffset) 358207340Sjkim{ 359207340Sjkim AML_RESOURCE *Descriptor; 360207340Sjkim ACPI_PARSE_OBJECT *InitializerOp; 361207340Sjkim ACPI_PARSE_OBJECT *MinOp = NULL; 362207340Sjkim ACPI_PARSE_OBJECT *MaxOp = NULL; 363207340Sjkim ACPI_PARSE_OBJECT *LengthOp = NULL; 364207340Sjkim ACPI_PARSE_OBJECT *AlignOp = NULL; 365207340Sjkim ASL_RESOURCE_NODE *Rnode; 366207340Sjkim UINT32 i; 367207340Sjkim 368207340Sjkim 369207340Sjkim InitializerOp = Op->Asl.Child; 370207340Sjkim Rnode = RsAllocateResourceNode (sizeof (AML_RESOURCE_IO)); 371207340Sjkim 372207340Sjkim Descriptor = Rnode->Buffer; 373207340Sjkim Descriptor->Io.DescriptorType = ACPI_RESOURCE_NAME_IO | 374207340Sjkim ASL_RDESC_IO_SIZE; 375207340Sjkim 376207340Sjkim /* Process all child initialization nodes */ 377207340Sjkim 378207340Sjkim for (i = 0; InitializerOp; i++) 379207340Sjkim { 380207340Sjkim switch (i) 381207340Sjkim { 382207340Sjkim case 0: /* Decode size */ 383207340Sjkim 384207340Sjkim RsSetFlagBits (&Descriptor->Io.Flags, InitializerOp, 0, 1); 385207340Sjkim RsCreateBitField (InitializerOp, ACPI_RESTAG_DECODE, 386207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Io.Flags), 0); 387207340Sjkim break; 388207340Sjkim 389207340Sjkim case 1: /* Min Address */ 390207340Sjkim 391207340Sjkim Descriptor->Io.Minimum = 392207340Sjkim (UINT16) InitializerOp->Asl.Value.Integer; 393228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_MINADDR, 394207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Io.Minimum)); 395207340Sjkim MinOp = InitializerOp; 396207340Sjkim break; 397207340Sjkim 398207340Sjkim case 2: /* Max Address */ 399207340Sjkim 400207340Sjkim Descriptor->Io.Maximum = 401207340Sjkim (UINT16) InitializerOp->Asl.Value.Integer; 402228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_MAXADDR, 403207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Io.Maximum)); 404207340Sjkim MaxOp = InitializerOp; 405207340Sjkim break; 406207340Sjkim 407207340Sjkim case 3: /* Alignment */ 408207340Sjkim 409207340Sjkim Descriptor->Io.Alignment = 410207340Sjkim (UINT8) InitializerOp->Asl.Value.Integer; 411207340Sjkim RsCreateByteField (InitializerOp, ACPI_RESTAG_ALIGNMENT, 412207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Io.Alignment)); 413207340Sjkim AlignOp = InitializerOp; 414207340Sjkim break; 415207340Sjkim 416207340Sjkim case 4: /* Length */ 417207340Sjkim 418207340Sjkim Descriptor->Io.AddressLength = 419207340Sjkim (UINT8) InitializerOp->Asl.Value.Integer; 420207340Sjkim RsCreateByteField (InitializerOp, ACPI_RESTAG_LENGTH, 421207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Io.AddressLength)); 422207340Sjkim LengthOp = InitializerOp; 423207340Sjkim break; 424207340Sjkim 425207340Sjkim case 5: /* Name */ 426207340Sjkim 427207340Sjkim UtAttachNamepathToOwner (Op, InitializerOp); 428207340Sjkim break; 429207340Sjkim 430207340Sjkim default: 431207340Sjkim 432207340Sjkim AslError (ASL_ERROR, ASL_MSG_RESOURCE_LIST, InitializerOp, NULL); 433207340Sjkim break; 434207340Sjkim } 435207340Sjkim 436207340Sjkim InitializerOp = RsCompleteNodeAndGetNext (InitializerOp); 437207340Sjkim } 438207340Sjkim 439207340Sjkim /* Validate the Min/Max/Len/Align values */ 440207340Sjkim 441207340Sjkim RsSmallAddressCheck (ACPI_RESOURCE_NAME_IO, 442207340Sjkim Descriptor->Io.Minimum, 443207340Sjkim Descriptor->Io.Maximum, 444207340Sjkim Descriptor->Io.AddressLength, 445207340Sjkim Descriptor->Io.Alignment, 446213806Sjkim MinOp, MaxOp, LengthOp, AlignOp, Op); 447207340Sjkim 448207340Sjkim return (Rnode); 449207340Sjkim} 450207340Sjkim 451207340Sjkim 452207340Sjkim/******************************************************************************* 453207340Sjkim * 454207340Sjkim * FUNCTION: RsDoIrqDescriptor 455207340Sjkim * 456207340Sjkim * PARAMETERS: Op - Parent resource descriptor parse node 457207340Sjkim * CurrentByteOffset - Offset into the resource template AML 458207340Sjkim * buffer (to track references to the desc) 459207340Sjkim * 460207340Sjkim * RETURN: Completed resource node 461207340Sjkim * 462207340Sjkim * DESCRIPTION: Construct a short "IRQ" descriptor 463207340Sjkim * 464207340Sjkim ******************************************************************************/ 465207340Sjkim 466207340SjkimASL_RESOURCE_NODE * 467207340SjkimRsDoIrqDescriptor ( 468207340Sjkim ACPI_PARSE_OBJECT *Op, 469207340Sjkim UINT32 CurrentByteOffset) 470207340Sjkim{ 471207340Sjkim AML_RESOURCE *Descriptor; 472207340Sjkim ACPI_PARSE_OBJECT *InitializerOp; 473207340Sjkim ASL_RESOURCE_NODE *Rnode; 474207340Sjkim UINT32 Interrupts = 0; 475207340Sjkim UINT16 IrqMask = 0; 476207340Sjkim UINT32 i; 477207340Sjkim 478207340Sjkim 479207340Sjkim InitializerOp = Op->Asl.Child; 480207340Sjkim Rnode = RsAllocateResourceNode (sizeof (AML_RESOURCE_IRQ)); 481207340Sjkim 482207340Sjkim /* Length = 3 (with flag byte) */ 483207340Sjkim 484207340Sjkim Descriptor = Rnode->Buffer; 485207340Sjkim Descriptor->Irq.DescriptorType = ACPI_RESOURCE_NAME_IRQ | 486207340Sjkim (ASL_RDESC_IRQ_SIZE + 0x01); 487207340Sjkim 488207340Sjkim /* Process all child initialization nodes */ 489207340Sjkim 490207340Sjkim for (i = 0; InitializerOp; i++) 491207340Sjkim { 492207340Sjkim switch (i) 493207340Sjkim { 494207340Sjkim case 0: /* Interrupt Type (or Mode - edge/level) */ 495207340Sjkim 496207340Sjkim RsSetFlagBits (&Descriptor->Irq.Flags, InitializerOp, 0, 1); 497207340Sjkim RsCreateBitField (InitializerOp, ACPI_RESTAG_INTERRUPTTYPE, 498207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Irq.Flags), 0); 499207340Sjkim break; 500207340Sjkim 501207340Sjkim case 1: /* Interrupt Level (or Polarity - Active high/low) */ 502207340Sjkim 503207340Sjkim RsSetFlagBits (&Descriptor->Irq.Flags, InitializerOp, 3, 0); 504207340Sjkim RsCreateBitField (InitializerOp, ACPI_RESTAG_INTERRUPTLEVEL, 505207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Irq.Flags), 3); 506207340Sjkim break; 507207340Sjkim 508207340Sjkim case 2: /* Share Type - Default: exclusive (0) */ 509207340Sjkim 510207340Sjkim RsSetFlagBits (&Descriptor->Irq.Flags, InitializerOp, 4, 0); 511207340Sjkim RsCreateBitField (InitializerOp, ACPI_RESTAG_INTERRUPTSHARE, 512207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Irq.Flags), 4); 513207340Sjkim break; 514207340Sjkim 515207340Sjkim case 3: /* Name */ 516207340Sjkim 517207340Sjkim UtAttachNamepathToOwner (Op, InitializerOp); 518207340Sjkim break; 519207340Sjkim 520207340Sjkim default: 521207340Sjkim 522207340Sjkim /* All IRQ bytes are handled here, after the flags and name */ 523207340Sjkim 524207340Sjkim if (InitializerOp->Asl.ParseOpcode != PARSEOP_DEFAULT_ARG) 525207340Sjkim { 526207340Sjkim /* Up to 16 interrupts can be specified in the list */ 527207340Sjkim 528207340Sjkim Interrupts++; 529207340Sjkim if (Interrupts > 16) 530207340Sjkim { 531207340Sjkim AslError (ASL_ERROR, ASL_MSG_INTERRUPT_LIST, 532207340Sjkim InitializerOp, NULL); 533207340Sjkim return (Rnode); 534207340Sjkim } 535207340Sjkim 536207340Sjkim /* Only interrupts 0-15 are allowed (mask is 16 bits) */ 537207340Sjkim 538207340Sjkim if (InitializerOp->Asl.Value.Integer > 15) 539207340Sjkim { 540207340Sjkim AslError (ASL_ERROR, ASL_MSG_INTERRUPT_NUMBER, 541207340Sjkim InitializerOp, NULL); 542207340Sjkim } 543207340Sjkim else 544207340Sjkim { 545207340Sjkim IrqMask |= (1 << (UINT8) InitializerOp->Asl.Value.Integer); 546207340Sjkim } 547207340Sjkim } 548207340Sjkim 549207340Sjkim /* Case 4: First IRQ value in list */ 550207340Sjkim 551207340Sjkim if (i == 4) 552207340Sjkim { 553207340Sjkim /* Check now for duplicates in list */ 554207340Sjkim 555207340Sjkim RsCheckListForDuplicates (InitializerOp); 556207340Sjkim 557207340Sjkim /* Create a named field at the start of the list */ 558207340Sjkim 559228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_INTERRUPT, 560207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Irq.IrqMask)); 561207340Sjkim } 562207340Sjkim break; 563207340Sjkim } 564207340Sjkim 565207340Sjkim InitializerOp = RsCompleteNodeAndGetNext (InitializerOp); 566207340Sjkim } 567207340Sjkim 568207340Sjkim /* Now we can set the channel mask */ 569207340Sjkim 570207340Sjkim Descriptor->Irq.IrqMask = IrqMask; 571207340Sjkim return (Rnode); 572207340Sjkim} 573207340Sjkim 574207340Sjkim 575207340Sjkim/******************************************************************************* 576207340Sjkim * 577207340Sjkim * FUNCTION: RsDoIrqNoFlagsDescriptor 578207340Sjkim * 579207340Sjkim * PARAMETERS: Op - Parent resource descriptor parse node 580207340Sjkim * CurrentByteOffset - Offset into the resource template AML 581207340Sjkim * buffer (to track references to the desc) 582207340Sjkim * 583207340Sjkim * RETURN: Completed resource node 584207340Sjkim * 585207340Sjkim * DESCRIPTION: Construct a short "IRQNoFlags" descriptor 586207340Sjkim * 587207340Sjkim ******************************************************************************/ 588207340Sjkim 589207340SjkimASL_RESOURCE_NODE * 590207340SjkimRsDoIrqNoFlagsDescriptor ( 591207340Sjkim ACPI_PARSE_OBJECT *Op, 592207340Sjkim UINT32 CurrentByteOffset) 593207340Sjkim{ 594207340Sjkim AML_RESOURCE *Descriptor; 595207340Sjkim ACPI_PARSE_OBJECT *InitializerOp; 596207340Sjkim ASL_RESOURCE_NODE *Rnode; 597207340Sjkim UINT16 IrqMask = 0; 598207340Sjkim UINT32 Interrupts = 0; 599207340Sjkim UINT32 i; 600207340Sjkim 601207340Sjkim 602207340Sjkim InitializerOp = Op->Asl.Child; 603207340Sjkim Rnode = RsAllocateResourceNode (sizeof (AML_RESOURCE_IRQ_NOFLAGS)); 604207340Sjkim 605207340Sjkim Descriptor = Rnode->Buffer; 606207340Sjkim Descriptor->Irq.DescriptorType = ACPI_RESOURCE_NAME_IRQ | 607207340Sjkim ASL_RDESC_IRQ_SIZE; 608207340Sjkim 609207340Sjkim /* Process all child initialization nodes */ 610207340Sjkim 611207340Sjkim for (i = 0; InitializerOp; i++) 612207340Sjkim { 613207340Sjkim switch (i) 614207340Sjkim { 615207340Sjkim case 0: /* Name */ 616207340Sjkim 617207340Sjkim UtAttachNamepathToOwner (Op, InitializerOp); 618207340Sjkim break; 619207340Sjkim 620207340Sjkim default: 621207340Sjkim 622207340Sjkim /* IRQ bytes are handled here, after the flags and name */ 623207340Sjkim 624207340Sjkim if (InitializerOp->Asl.ParseOpcode != PARSEOP_DEFAULT_ARG) 625207340Sjkim { 626207340Sjkim /* Up to 16 interrupts can be specified in the list */ 627207340Sjkim 628207340Sjkim Interrupts++; 629207340Sjkim if (Interrupts > 16) 630207340Sjkim { 631207340Sjkim AslError (ASL_ERROR, ASL_MSG_INTERRUPT_LIST, 632207340Sjkim InitializerOp, NULL); 633207340Sjkim return (Rnode); 634207340Sjkim } 635207340Sjkim 636207340Sjkim /* Only interrupts 0-15 are allowed (mask is 16 bits) */ 637207340Sjkim 638207340Sjkim if (InitializerOp->Asl.Value.Integer > 15) 639207340Sjkim { 640207340Sjkim AslError (ASL_ERROR, ASL_MSG_INTERRUPT_NUMBER, 641207340Sjkim InitializerOp, NULL); 642207340Sjkim } 643207340Sjkim else 644207340Sjkim { 645207340Sjkim IrqMask |= (1 << ((UINT8) InitializerOp->Asl.Value.Integer)); 646207340Sjkim } 647207340Sjkim } 648207340Sjkim 649207340Sjkim /* Case 1: First IRQ value in list */ 650207340Sjkim 651207340Sjkim if (i == 1) 652207340Sjkim { 653207340Sjkim /* Check now for duplicates in list */ 654207340Sjkim 655207340Sjkim RsCheckListForDuplicates (InitializerOp); 656207340Sjkim 657207340Sjkim /* Create a named field at the start of the list */ 658207340Sjkim 659228110Sjkim RsCreateWordField (InitializerOp, ACPI_RESTAG_INTERRUPT, 660207340Sjkim CurrentByteOffset + ASL_RESDESC_OFFSET (Irq.IrqMask)); 661207340Sjkim } 662207340Sjkim break; 663207340Sjkim } 664207340Sjkim 665207340Sjkim InitializerOp = RsCompleteNodeAndGetNext (InitializerOp); 666207340Sjkim } 667207340Sjkim 668207340Sjkim /* Now we can set the interrupt mask */ 669207340Sjkim 670207340Sjkim Descriptor->Irq.IrqMask = IrqMask; 671207340Sjkim return (Rnode); 672207340Sjkim} 673